Variables, Constants, and Datatypes Reading Objective In this reading, you will be introduced to variables, constants, and datatypes in C. You will understand how memory space is allocated to variables in RAM. You will also understand how characters are internally represented as integers and how implicit and explicit type conversions are performed in C. Data in Computer Programs We write computer programs to solve real-world problems. For this, programs must be very efficient in handling real-world data. Programming languages have come up with different data types that support different kinds of data to address the need to represent real-world data in computer programs. Data in a program can be stored as a constant or a variable. A constant is a data item whose value remains fixed throughout the entire program. A variable is a data item whose value can be changed during the program’s execution. Variables are allocated a fixed memory location in the RAM from where we can read and modify the variable. For example, if we need to store the value of π in a program, we will use a constant. To iterate over a list of 20,000 items, we will use a variable to indicate the current position that we are reading and keep incrementing the value of that variable to iterate through the entire list. Variables in C Programming Language We can declare a variable by specifying the data type of the variable followed by the variable name. For example, int age, or float avg. • memory. Declaration of a variable allocates memory to that variable on the main • We can also declare more than one variable of a data type simultaneously by separating the variable names with a comma separator. For example, int age, marks. • Along with the declaration of the variables, we can also initialize them to some specific values. For example, int age = 20, marks = 80. If the variable is not initialized during declaration, it contains a junk value. • Let us consider the statement: int age = 20, marks = 80. The above statement declares two integer data type variables with age and marks as the variable names and also initializes them to the values 20 and 80, respectively. Since we have created two variables, we can change their values later in the program as follows: age = 22, marks = 70 • Every variable must be declared before it is used. Otherwise, the compiler would raise an error. • Certain rules to be followed while giving names to variables: ◦ Every variable name should start with an alphabet or an underscore and can contain alphabets, numbers, and underscores only. ◦ Variable names cannot be a keyword. Keywords in C are some reserved words for special purposes. Some examples of keywords are int, main, return, and struct. ◦ Variable names are case-sensitive, that is, Number and number are two different variable names. ◦ Preferably, variable names should be meaningful, denoting the value the variable will store. For example, age and number. • C is a typed programming language, meaning all the variables in C have a specific data type. Once we have declared the data type of a variable, it cannot be changed. • • • Fundamental data types in C are as follows: ◦ Integer (short, int, long, long long) ◦ Floating point (float, double, long double) ◦ Character (char) Some examples of variable declaration in different data types: ◦ int age = 21 ◦ float pi = 3.14 ◦ char ch = ‘S’ ◦ int amount1 = 45, amount2 = 500, amount3 = 999 Every datatype is associated with a fixed amount of storage. Constants in C Programming Language A constant is a data item whose value remains fixed throughout the entire program. C specifies a default datatype with every constant. For example, 25, 6.25, and ‘$’ are all constants. • The default data type of an integer in C is int. If the constant does not fit into an integer, a larger size data type is used to store the constant. • The default data type for a floating point number is double. • We can use suffixes to assign data types to constants other than their default datatypes. For integer constants, the suffix U or you can be used to make them unsigned integers, suffix L or l can be used to make them as long integers. When a double constant is suffixed by f or F, it demotes the constant to a float datatype, and the suffix L or l promotes it to a long double datatype. • There are two ways of defining constants in C. ◦ Using a const qualifier In a variable declaration, we can add const qualifier in front of the declaration to tell the compiler that this variable declaration is a constant declaration, not a variable declaration. For example, const float pi = 3.14f; // here pi is a read-only value. Also, note that we have used ‘f’ as a suffix to indicate that the constant value 3.14 is to be interpreted as a float value, not a double value. ◦ Using symbolic constants #define We can use preprocessor directives to define constants in our code. For example, #define PI 3.14f // no semicolon used Before compiling the code, the compiler will replace all the occurrences of PI in our program with 3.14f. Note: It is good practice to use all capital letters when defining #define constants and to start all variables with a small letter. ◦ The difference between the two types of constants above is that in the first type, we have declared a constant that takes actual memory on RAM. Still, because we have specified the const qualifier in the declaration, the compiler won’t allow the value of this variable to be changed during the execution of the program. Whereas when we use #define, no variable is declared. The compiler is just replacing PI with 3.14f in our program before it starts compilation. Where and How is the Program Data Stored? !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/mSVR0oMQBiPsU4IagH0zQ_fcdf9ce904d1400baf9b9976cef2eaa1_Picture2.png?expiry=169050 2400000&hmac=8heSluCtG_0IBxM3IeCcpSUa2AzE-LvvM_02KFjnmek Figure 1: C program showing variable declaration. Consider the C program shown in Figure 1 above. Its main function has three variables declared: num1, num2, and num3. Where do these three variables get stored in the main memory? !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/_ve0Xb2RRbypW3blcGfcKA_5 6eabb91110841c78d5843ff433935a1_Picture4.png?expiry=1690502400000&hmac=mZIkE O35vKJKXiX6TkWEba3z6GPNGrQ2wIv_qCiOBsw Figure 2: Steps of program execution. We have noted that the compilation of a C program creates an executable stored on the hard disk. When this executable file is executed, the operating system (OS) loads our C program into the RAM and executes it line by line on the CPU. Let us look closely at the memory allocated to the program in the main memory. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/ynRTqNwqSGW2NMaKdyapaw _356089926d0d410498fec1b7290b8ba1_Picture5.png?expiry=1690502400000&hmac=2mf6 BJ8AMqhThUAJUBhGqT2B6XUOhqLNOuqVH7LgiAg Figure 3: Memory allocation to a C program on RAM. When the OS loads the program into RAM, it allocates some memory to the program. As shown in Figure 3, the variables named in the program are stored in this space. Variable Types and Their Storage Variables in a C program occupy a fixed amount of RAM space on the RAM depending on their datatype. For example, an int variable will occupy 2 or 4 bytes depending on the compiler used to compile the program. Main memory is logically represented as a massive table of rows, where each row can store 8 bits. A bit stores a binary value of 0 or 1, sometimes called True or False. A set of 8 contiguous bits is known as a byte. Figure 4 shows a snapshot of how the RAM looks when an int variable is declared and initialized: int num = 4; Four bytes are allocated, as shown in addresses from 1004 through 1007, and the value of 4 is in these four bytes. Figure 5 shows different integer types supported by the C programming language and what the range of values that these datatypes can represent. Since any variable in C takes a finite amount of memory, it can be easily understood that there will be a certain limit on the number of values that it can represent. The precise size of all the datatypes is not explicitly defined in the C language definition. It is left up to the compiler to decide how much memory to allocate to those datatypes. However, we can still observe that allocated memory follows the order below: short, unsigned short <= int, unsigned int <= long, unsigned long <= long long, unsigned long long. It is also very easy to determine the number of bytes allotted to a particular variable. The sizeof() operator returns the number of bytes allotted to a variable. Its return type is unsigned long int. Figure 6 shows an example of a C program that computes the amount of memory allocated for variables of different datatypes and its output on execution. Please go to Coursera Labs and try to execute this code. You learn better when you execute the code yourself. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/MLVI220lQbegrSaBdNdAg_baaa172d646946d7ae5b8b7c524140a1_Picture6.png?expiry=1690502400000&hma c=G5_IvjD3RNe7Vqaaxlvw0KasQo-DVMvYOEvyCO4QJdg Figure 4: Visualization of some memory locations in RAM when a variable is declared and initialized. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/RQ5_30FWTuef0ikS1MNx_g_b 461982985db4b35b64a6c35431863a1_Picture7.png?expiry=1690502400000&hmac=bGcvIP aEumDuVWX5W49ii6a4inl8wa-pB-QCxHmqSR4 Figure 5: Integer datatypes supported by C programming language ds. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/cDttFfctQTmu_pSpx5Kbw_175c4a9926d745abb8eaf722926e14a1_Picture8.png?expiry=1690502400000&hmac= D3Cu34pbosmkc2gw3Oqrml4AKB2_PHiJFZYpwVUGP5M !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/oS2wgjbARGOrHCoh0Q23WA _eb663b63e9de48659ca7d8576e9f75a1_Picture9.png?expiry=1690502400000&hmac=uBvY xAQ-ofS8ZK1znw0edpcZd86Ipu7MGUojAjQCPo4 Figure 6: Example C program to show the working of sizeof() operator. Figure 7 shows the different types of floating-point datatypes supported by C, the number of bytes used by them, and their range in the form of mantissa and exponent. Please note that a double has a higher precision than a float in terms of the number of digits. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/1zRQiHwERGCY8FZWk3EaEg _357991b3f7204c979d268c2f7dc28fa1_Picture10.png?expiry=1690502400000&hmac=89G eqIuuLkIvJk2D6Mf_v2cZjAuBfV2vfzN_YrKtCO0 Figure 7: Types of Floating-Point Numbers in C. Character Types in C: We have heard about representing integers in binary format, but what about characters? How do computers represent characters in binary format? Computers use ASCII (American Standard Code for Information Interchange) character-encoding scheme. ASCII defines an encoding to represent English characters (a-z, A-z) along with the other symbols (!, @, #, $), punctuation marks (:, “, ‘, ?, /), numeric characters (0-9) and some non-printable characters as numbers, with each letter assigned to a number from 0 to 127. 8-bit ASCII is used in C so the char datatype is one byte wide. Fig 8 shows an ASCII chart that shows how different characters are represented in ASCII character-encoding scheme. Character variables are stored in the memory as integers only, and therefore, we can perform computations using them. For instance, in the example given below, %c format specifier tells printf() to interpret ch1 or ch2 as a character, and %d tells printf() to interpret ch1 or ch2 as an integer while printing. char ch1 = ‘A’, ch2; printf(“%c\t%d\n”, ch1, ch1); // prints A 65 on the screen ch2 = ch1 + 1; // char variables can be used for computation just like integers printf(“%c\t%d\n”, ch2, ch2); // prints B 66 on the screen Nonprintable characters There are certain characters in ASCII like \n (newline), \t(tab), which cannot be printed on the screen. These are called non-printable characters. Refer to Figure 8 to find out more nonprintable characters. To print some special characters like ‘ or “ or \ , we should use a preceding \. See the example below. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/_PeYzOrbSVSmZR6WeT03yA_ 8fe91f761e7243b09e0ff4155c6276a1_Capture.JPG?expiry=1690502400000&hmac=rhbTM QzTHgVotPUdkrlLkUJaPtKjDrnjdPNbGsaIXuQ A string is a sequence of characters. In C, a string is implemented as an array of characters. (You will learn more about arrays and strings later!) A character literal in C is enclosed within single quotes, whereas a string literal in C is enclosed within double quotes. For example, “Welcome” is a string, ‘A’ is a character, “A” is a string containing only one character, and ‘Welcome’ will throw an error. !https://d3c33hcgiwev3.cloudfront.net/imageAssetProxy.v1/Sv8uSAgkS96FCHcziwplOw_9 951693873654f3fb715dbd61d9560a1_Picture11.gif?expiry=1690502400000&hmac=VbvJ3 YTBQVzE8nT3idwBu53PtnnZCF7X8XfpWvrSDp4 Figure 8 - ASCII chart. Type Conversions: Type conversion in C allows us to tell the compiler to interpret the datatype of a variable differently in a particular statement. Note that type conversion does not change the datatype of a variable; it just instructs the compiler to interpret a variable as a different datatype while executing a particular instruction. There are two types of type conversions, implicit and explicit. • Implicit Type Conversion ◦ The compiler performs implicit type conversion when there’s an expression involving operands of different datatypes, in which case the lowersized operand would is elevated to the higher-sized operand. For example, int a = 2; float b = 3.5, c; c = a + b; /* value of a in the expression is temporarily promoted to float and two floats get added. The resultant float is again stored as integer in c. ◦ Rules for implicit type conversion are as follows: ▪ If either operand is a long double, convert the other into a long double. ▪ Otherwise, if either operand is double, convert the other into double. ▪ into float. Otherwise, if either operand is float, convert the other ▪ Otherwise, convert char and short to int. ▪ Then, if either operand is long, convert the other to long. ◦ For example, float X = 0.2; double A = X/0.1; /* here X will be typecasted to a double variable and then the division will be performed. A = 2.000000 after computation is over */ • Explicit Type Conversion ◦ In explicit type conversion, we explicitly instruct the compiler to interpret the datatype of a particular variable differently while executing a particular instruction. Implicit type conversion is automatically done by the compiler, whereas explicit type conversion must be done by the programmer explicitly. ◦ To do explicit type conversion, we can put the desired datatype of the variable in parentheses in front of the variable. For example, int a = 3, b = 100; double c; c = b/a; printf("c = %lf\n",c); // c = 33.000000 c = b/(double)a; /* here we perform explicit type conversion of a to double, and now the compiler will convert the type of b to double implicitly */ printf("c = %lf\n",c); // c = 33.333333 Reading Summary: In this reading, you have learned the following: ● What a variable is and what a constant is ● Declare and initialize variables and constants of different datatypes in C programs ● How variables in a program get space allocated in the RAM based on their types ● Find the size of different types of variables in C ● Differentiate between integer and floating-point variables ● Declare, print, and perform arithmetic operations on character variables ● Understand implicit type conversions in C and perform explicit type conversions in C