Types and Variables
Fundamental to any programming language is the means of associating names (called variables) with values. In most all programming languages, these variables represent data of different types. To see more completely how C handles these issues, you will need to read the following sections from the textbook.
- King: Sections 7.1-7.4, 4.1-4.3, pages 125-148, 53-62
Introduction
In Scheme, a variable (or identifier or parameter) can represent any type of data, and the type of a variable may change from one call of a procedure to another. For example, consider the following Scheme procedure that adds all numbers on a list or its sublists:
(define sum-numbers
(lambda (lst)
(cond [(number? lst) lst]
[(not (list? lst)) 0]
[(null? lst) 0]
[else
(+ (sum-numbers (car lst))
(sum-numbers (cdr lst)))))))
When sum-numbers is called:
(sum-numbers '((1) 2.0 four ((3/4) (five) 6)))
the parameter lst starts as a list, but various calls
will give lst various values, including sublists,
integers (e.g., 1, 6), real numbers (2.0), fractions (3/4), and
symbols (e.g., four, five). At the end of this
example, sum-numbers returns 9.75.
C is an older language than Scheme and is more restrictive in how it handles types of variables. In C, the data type of each variable must be declared before the variable is used in a program (or procedure). Once declared, the data type cannot change; values can change, but not the type of data.
When you start programming in C, you need to be familiar with the few primitive types of variables provided as a core part of the language. Often processing proceeds according to the type of data involved. However, in some processing situations, C allows for implicit and explicit type conversions between these storage classes. In the accompanying lab, you will perform different operations and examine the results.
Primitive Types
C has four primitive types:
char c; /* a character */
int i; /* an integer */
float f; /* a real number (single-precision)*/
double d; /* a real number that needs twice the space as a float (double-precision) */
The following notes provide some background about each of these data types,
-
a
charis a character that you might type at the keyboard, such asA,q,;(semi-colon),*(asterisk), etc.
In C, acharvalue is identified with single quotes, such as 'a', 'b', 'A', '8', ';', etc. Note: some of these characters can be typed on the keyboard (such as a tab or a return) but are difficult to represent in text. We type special characters using two symbols (such as '\n' for a return key or '\t' for a tab), but they actually represent a single character in the program. -
an
intis an integer (a whole number with no decimal point) -
a
floatand adoublerepresent a real number (a number with a decimal point).-
a
floattypically maintains about 7 digits of accuracy, and requires a relatively small amount of memory -
a
doubletypically maintains about 16 digits of accuracy, and requires twice the amount of space required by afloat
-
a
As we shall discuss in several weeks, these types of data are represented in different ways within a computer.
- Each data type takes up a different amount storage.
- The amount of storage may vary from one machine to another.
-
Each data type has a limited range of values.
- Details of these limits are given in pages 591 - 593 in the text book.
-
For example, an
intusually has values between -2,147,483,648 (INT_MINinlimits.h) and 2,147,483,647 (INT_MAXinlimits.h), inclusive.
Computations with ints and doubles
C provides common arithmetic operations for both ints
and doubles, with an extra capability for ints.
-
+and-represent addition and subtraction -
*and/represent multiplication and division -
for
ints,%represents integer remainder.
Basic rules:
- Arithmetic with integers is efficient and fast, and the result is always an integer. Note that this can give unexpected results when dividing two integers!!
- Arithmetic with floating point numbers may be somewhat slower, and the result is always a floating point number.
- Arithmetic involving an integer and a floating point number proceeds in two steps: first the integer is converted to a floating point number, and second the operation is applied to the two floating point numbers, and the result is always a floating point number.
Incrementing and Decrementing Numbers
Suppose you have a counter variable days that counts
down the number of days you have left for the summer. Every day that
passes, you need to decrement the number of days to get your
countdown going. You could do it like this:
days = days - 1;
This would mean that your are taking the number of days, subtracting
1 from it, and setting that as my new days value.
However, a shortcut to saying that the new value of days is the
old value of days minus one may be written as follows.
days -= 1;
You can do a variety of operations just like this:
-
a += bmeansa = a+b -
a /= bmeansa = a/b -
a *= bmeansa = a*b
In practice, 1 is the most common value to add or subtract from a
variable, and C provides two special ways to increment by 1. For a
variable a,
-
++ais called a pre-increment operation: add 1 to a before anything else happens in the expression. -
a++is called a post-increment operation: add 1 to a after anything else happens in the expression.
Characters
In C, a character is stored in a coded form as an integer,
typically between 0 and 255. (Historically, the coded form used numbers 0
to 127, but the extended code now uses codes over the full range 0 to
255.) Thus, a char is considered to be an integer with
a restricted size. For the most part, we do not care what the
internal code is for an integer—conceptually, we just have a
character. Usually the underlying numerical code is the American Standard
Code for Information Interchange or ASCII. However, the C
standard (cf.
Section 5.2
) does not require that compilers use ASCII, and therefore the ASCII code should not
be relied upon when writing programs that you may want to compile and run on different computers.