Professional Documents
Culture Documents
Lesson 4
Data Types
James C.C. Cheng
Department of Computer Science
National Chiao Tung University
The basic data types
There are 13 basic data types in C
Name Size (byte) Range
char 1 -128 to 127
unsigned char 1 0 to 255
short 2 -32768 to 32767
unsigned short 2 0 to 65535
int 4 -231 to 231 - 1
unsigned int 4 0 to 232 - 1
long 4 -231 to 231 - 1
unsigned long 4 0 to 232 - 1
__int64, long long 8 -263 to 263 – 1
unsigned __int64 8 0 to 264 - 1
float 4 ±(1.175494351e-38 to 3.402823466e38 )
double 8 ±(2.2250738585072014e-308 to
1.7976931348623158e308 )
long double 12 in DevC++, 8 in MSC x86 80-bit extended precision format
In C++, bool represents boolean value, true or false.
The size of bool depends on compiler, 1 byte in most case. 2
The basic data types
sizeof operator
return the number of byte for a variable or a data type
size_t sizeof( name );
size_t
In 32-bit environment: unsigned long
In 64-bit environment: unsigned long long
sizeof(type name)
ex: sizeof(int); sizeof(double);
sizeof(variable name)
ex: int x; sizeof(x); double d; sizeof(d);
Integers
The integer data types are:
bool, char, short, int, long, __int64
bool in C99: #include <stdbool.h>
unsigned char, unsigned short, unsigned int, unsigned long,
unsigned __int64
4
Integers
Decimal system
Each digit = {0, 1, …, 9 }
347210 = ( 3 x 103 ) + ( 4 x 102 ) + ( 7 x 101 ) + ( 2 x 100 )
Binary system
Each digit = {0, 1}
Binary Decimal
10112 = (1 x 23)10 + (0 x 22)10 + (1 x 21)10 + (1 x 20)10 = 1110
Decimal Binary
13 mod 2 = 1
13/2 = 6 mod 2 = 0
1310 = 11012
6/2 = 3 mod 2 = 1
3/2 = 1 mod 2 = 1
1/2 =0
Addition: 1+0 = 12 ; 1+1 = 102
Subtraction: 1-0 = 12 ; 10-1 = 12
5
Integers
Hexadecimal system
Each digit = {0-9, A, B, C, D, E, F}
Hex Decimal
3A7C = (3 x 163)10 + (10 x 162)10 + (7 x 161)10 + (12 x 160)10
= 1497210
Decimal Hex
Method 1: the same as Dec binary
Method 2: decbinhex
Addition
(2+7)16 = 916
(1+9)16 = A16
(2+B)16 = D16
(9+9)16 = 1216
Subtraction
(5-2)16 = 316
(F-2)16 = D16
(10-1)16 = F16 6
Integers
Binary Hex Hex Binary
0 0000
Grouping each 4 digits from the smallest digit
1 0001
11001110101101 = 0011,0011,1010,1101
2 0010
Check the hex bin table 3 0011
0011,0011,1010,1101 = 33AD 4 0100
5 0101
6 0110
7 0111
8 1000
9 1001
A 1010
B 1011
C 1100
D 1101
E 1110
F 1111
7
Integers
The limits of unsigned integers
1 bit: #include <limits.h>
0, 1 …
4 bit: unsigned char uc = UCHAR_MAX;
unsigned short us = USHRT_MAX;
0 ~ (24 – 1)10 = 0 ~ 1510
unsigned int u = UINT_MAX;
1 byte: unsigned long ul = ULONG_MAX;
0 ~ (28 – 1)10 = 0 ~ 25510 unsigned long long ull = ULLONG_MAX;
2 byte:
0 ~ (216 – 1)10 = 0 ~ 65,53510
4 byte:
0 ~ (232 – 1)10 = 0 ~ 4,294,967,29510
8 byte:
0 ~ (264 – 1)10 = 0 ~ 18,446,744,073,709,551,61510
8
Integers
The limits of signed integers
#include <limits.h>
…
char c = CHAR_MIN;
c = CHAR_MAX;
short s = SHRT_MIN;
s = SHRT_MAX;
int i = INT_MIN;
i = INT_MAX;
long l = LONG_MIN;
l = LONG_MAX;
long long ll = LLONG_MIN;
ll = LLONG_MAX;
9
Integers
Signed integer
How to store a signed integer?
Method 1: Sign bit
1 0 0 1 1 0 1 1 = -27
Sign bit
0 0 0 1 1 0 1 1 = 27
10
Integers
Signed integer
Method 2: One’s complement
27 = 0001,10112
-27 = -(0001,10112) 0/1 inversion 1110,01002
The range is ( 0 ~ 27 – 1) = (0 ~ 127)
Pros:
Simple
No addition and subtraction problems
1110,01002 + 0001,10112 = 1111,11112 -27 + 27 = -0
1110,01002 + 0000,00012 = 1110,01012 -27 + 1 = -26
Cons:
Negative zero
11
Integers
Signed integer
Method 3: Two’s complement
27 = 0001,10112
-27 = 1,0000,00002 - 0001,10112 = 1110,01012
The range is - 27 ~ -1, 0, 1 ~ (27 – 1) = -128 ~ 127
Pros:
No negative zero
No addition and subtraction problems
1110,01012 + 0001,10112 =
1,0000,00002 (max 8 bit) = 0000,00002 -27 + 27 = 0
1110,01012 + 0000,00012 = 1110,01102
= -(1,0000,00002 - 1110,01102 ) = -(0001,1010)2 -27 + 1 = -26
Cons:
It needs more conversion cost
12
Integers
Constants:
bool bT = true, bF = false, bTrue = 5438, bFalse = 0;
The zero is false; Non-zero is true.
char cA = ‘A’, cB = 66, cC= 65603, cD = 0x43, cE = 0105, cEnter = ‘\n’;
Hex constant: Using the prefix "0x"
Octal constant: Using the prefix "0"
short i = 10, j = 32767, k = -32768, s = 32768, t = -32769;
int x = 10, y = -100, z = 0x02AB2F;
int nMax = 2147483647;
int nMinA = -2147483648; // It causes a warning message
- 2147483648 - ( 2147483648 )
13
Integers
Constants:
long n = 120, m = 12345L, a = 0xFFFFL;
long integer constant : Using the suffix “L”
__int64 nn = 10, mm = 9876543210LL;
long long constant : Using the suffix “LL”
64-bit integer in scanf and printf: ll or I64
__int64 nn = 10;
long long mm = 9876543210LL ;
scanf("%I64d%lld", &nn, &mm);
printf("%lld, %I64d \n", nn, mm); // OK, using “ll” or “I64”
// Notice that "l" is lowercase. "L" means "long double", %Ld ==> %d
nn = 7; mm = 1;
printf("%d, %I64d \n", nn, mm); // In x86, the second output is wrong!?
07, 00, 00, 00 00, 00, 00, 00 01, 00, 00, 00 00, 00, 00, 00
14
nn mm
Integers
Constants:
unsigned char, unsigned short and unsigned int
unsigned char uc = -1;
unsigned short us = -1;
unsigned int ui = -1;
printf("%u, %u, %u\n", uc, us, ui);
char c = -1;
printf("%02hhX\n", c); // Failed in DevC++
short s = -1;
printf("%04hX\n", s);
long l = -1L;
printf("%08lX\n", l);
long long ll = -1LL;
printf("%016llX\n", ll);
17
Integers
Implicit typecast
small large
short s1 = 10;
int n1 = 0xFF0000;
if(n1 > s1) // short int
printf("Hello\n");
signed unsigned
unsigned int u= 0;
int i = -1;
if(i>u) // int unsigned int
printf("-1 > 0\n");
18
Float point numbers
float , 32-bit IEEE-754 float point number
double , 64-bit IEEE-754 float point number
long double
In VC++, long double = double
In GCC 4.3 or above, sizeof( long double) is 12 byte,
In x86 environment, it only uses 10 byte
Why it need 12 byte? In 32-bit environment, the data access
unit is 4 byte.
x86 80-bit extended precision format
19
Float point numbers
Decimal fraction Binary?
0.5 10 = 2-1 10 = 0.1 2
0.25 10 = 2-2 10 = 0.01 2
0.125 10 = 2-3 10 = 0.001 2
….
0.10112 = (1 x 2-1) 10 + (0 x 2-2) 10 + (1 x 2-3) 10 + (1 x 2-4) 10
= 0.510 + 0.12510 + 0.062510
= 0.687510
0.37510 = 0.011
0.375 * 2 = 0.75
0.75 * 2 = 1.5
0.5 * 2 = 1.0
Some decimal fraction cannot be converted to binary system
0.410 = 0.001100110011……2
= 0.00112
20
Float point numbers
Decimal fraction Binary?
integer part binary
fraction part binary
13.562510 = 1101.10012
1310 = 1101
0.562510 = 0.10012
21
Float point numbers
IEEE 754 (The IEEE Standard for Floating-Point Arithmetic)
IEEE, Institute of Electrical and Electronics Engineers 國際電子電機學會
32-bit IEEE-754
Sign: 1bit
Exponent: 8 bit (127 offset)
Fraction: 23 bit
64-bit IEEE-754
Sign: 1bit
Exponent: 11 bit (1023 offset)
Fraction: 52 bit
mantissa
22
Float point numbers
IEEE 754 (The IEEE Standard for Floating-Point Arithmetic)
Example: 13.562510
= 1101.10012
= 1.10110012 * 23
24
Float point numbers
Addition and subtraction
13.562510 + 0.1562510 = 13.7187510
= (-1)0 * 23 * 1.10110012 + (-1)0 * 2-3 * 1.012
= 23 * 1.10110012 + 23 * 2-6 * 1.012
= 23 * 1.10110012 + 23 * 0.000001012
= 23 * 1.101101112
= 13.7187510
1234567.1510
= 1,0010,1101,0110,1000,0111. 0010,0110,0110,... 2
= 1. 0010,1101,0110,1000,0111 0010,0110,0110... 2 * 220
For 32 bit float:
= (-1)0 * 1. 0010,1101,0110,1000,0111 0010,0110,0110... 2 * 2147-127
Sign = 0
Exponent = 147 = 100100112
Fraction (23 bit) = 0010,1101,0110,1000,0111 0010,0110,0110 2 Truncation
= 0010,1101,0110,1000,0111 001 2 (1234567.125) 26
Float point numbers
Limits
Float Values (b = bias)
0 00..00 00..00 0
00..01~ Positive Denormalized Real
0 00..00
11..11 0.f × 2(-b+1)
00..01~ Positive Normalized Real
0 XX..XX
11..10 1.f × 2(e-b)
0 11..11 00..00 +Infinity
00..01~
0 11..11 NaN
11..11
27
Float point numbers
Limits
1 00..00 00..00 -0
28
Float point numbers
Limits
#include <float.h>
…
float f = FLT_MIN;
f = FLT_MAX;
double d = DBL_MIN;
d = DBL_MAX;
long double ld = LDBL_MIN;
ld = LDBL_MAX;
printf("%f\n", f);
printf("%f\n", d);
printf("%Lf\n", ld); // only in GCC 4.3 or above
29
Float point numbers
printf()
float will be converted to double
%f, %e, %E, %g, and %G need 8 byte argument
%+width+.precision + {f/e/E/g/G},
width: the minimum number of characters printed, if width is not
given, all characters of the value are printed.
precision:
for f/e/E : the number of digits after the decimal point,
for g/G: the maximum number of significant digits printed.
default is six
float r = 0.00000123;
printf("%10.8f, %4.2e, %4.2g\n", r, r, r);
Output:
0.00000123, 1.23e-006, 1.2e-006
30
Float point numbers
scanf()
%f: float, 4 byte data
%lf: double 8 byte data
%Lf: long double
Only in GCC 4.3 or above *.c file
G++ does not accept %Lf
31
Float point numbers
Constants:
float f = 1.1234f;
Using the suffix "f"
double r0 = 1.12345, r1 = 123, r2 = 0x64, r3 = 123LLU;
Without any prefix and suffix
Typecast
integer float
float fx = 33.3f;
printf("%f\n", fx * 2 / 3 );
float double
#include <float.h>
…
float fx = 0.0f;
double dx = fx + DBL_MIN;
printf("%f\n", dx);
32
Float point numbers
Never check a floating number to EQUAL a value
float A = 1.2f;
float B = 12.0f;
scanf("%f%f", &A, &B); // type 1.2 and 12
float D = A - B / 10.0f;
// D = 1.2 – 12/10.0 should be zero
if(D == 0.0) // Oops!
printf("!\n");
else
printf("%f\n", D); // This line will be show up
33
Float point numbers
Be careful with using a floating number to be an iterator
float i;
for(i=0.0f; i<=1.0f; i+=0.1f)
printf("%f\n", i);
34
Union
One memory space to be accessed as different data types
The size of the union is at least the size of the largest member.
union U{
unsigned long i;
float f;
};
int main(){
U u;
u.f = 13.5625f;
char a = 'A';
printf("%c: %d\n", a, a);
a = '9';
printf("%c: %d\n", a, a);
a = 'xyz';
printf("%c: %d\n", a, a);
36
Characters
Escape Sequences
char a = '\n', b = '\t', c= '\b';
\n: (10) newline
char d = '\r', i = '\'', j = '\"';
\t: (9) tab char f = '\\', g = '\0';
\b: (8) backspace
\r: (13) return key
In MS Windows, the end of line consists of two characters: \r\n (13, 10)
\': single quotation
\": double quotation
\\: backslash
\0: null
\OOO: OOO is 3-digit octal ASCII
char e = '\050',
\xOO: OO is 2-digit hex ASCII
char i = '\x41',
37
Strings
A character array
The last character of a string must be \0
Constant string: Using the double quotation marks " "
String declaration and initialization:
char s1[5] = "abcd"; // a writable char array
char s2[5] = {'A', 'B', 'C', 'D', 0}; // a writable char array
char s3[] = "xyz"; // a writable char array
char s4[] = { 'X', 'Y', 'Z', 0}; // a writable char array
char* s5 = "uvw"; // a char pointer that points a read-only data
38
Strings
Misuse
char s1[] = "abcd";
char s2[] = "ABCD";
s1 = s2;
// Compiling error! The array name cannot be an l-value
side effect
A expression returns one or more additional values.
That means it modifies some observable state.
39
Strings
scanf()
char A[20] = {0}; // Declare a string of 20 zero characters
scanf("%s", A); // type "ABC EFG XYZ"
printf("%s\n", A);
40
Strings
scanf()
%[^ ]: Read the characters except the specified characters
41
Strings
gets()
char* gets ( char *s);
It reads characters from the stdin and stores them into s until a newline
character or the end-of-file is reached.
On success, it returns s. Otherwise, it returns NULL
#include <stdio.h>
…
char A[100] = {0};
while( gets(A) != NULL ){
printf("%s\n", A);
}
42
Typecast
Change the data type of variable
x = (x's type name) y;
Ex:
int n = 1234;
float f = (float) n;
char c = (char) f;
double d = (double) c;
43
#define
The text replacement
Usage:
#define replacement target_text
Ex:
#define PI 3.14159
#define EXP 2.71828
#define NULL_STR
double p = PI;
printf("%f\n", p); // 3.14159
printf("%f\n", EXP); // 2.71828
printf("%f\n", NULL_STR); // Compile Error
printf("%f\n", NULL_STREXP); // Compile Error
printf("%f\n", NULL_STR EXP); // 2.71828 44
#define
Macro, 巨集
Ex:
#define MIN_INT(x) (-2147483647 – 1)
#define INC(x) (++x)
#define ADD(x, y) (x+y) 請注意括號!
#define MIN(x, y) (x<y?x:y)
#define _MIN(x, y) x<y?x:ytice
45
#define
Do not use #define to define a data type
Ex:
#define uint unsigned int
uint a, b ;
// OK! a and b are unsigned int
46
typedef
To define a datatype
The usage:
typedef original_typename new_typename; 注意要加分號
EX:
47
練習題
設計一個函式,名為inverseN,用來反轉一個unsigned long
例如:12345則回傳54321;12321則回傳12321;0則回傳0
須注意overflow,若數字2223334445則回傳0並顯示overflow。
請用最節省空間方式完成,不可用64bit整數、字串及陣列
給一個double陣列A,用來儲存某數學函數的運算結果,即A[i] = f(ix)。
請寫一個函式來計算f 的微分: ′ ≅ ′ ≅
void dev(const double* A, double* B, int n);
其中A為輸入陣列,B為微分結果,n為陣列元素個數。
A[i] = 0 if i < 0 or i >= n
48
練習題
請設計generic min & max functions,可處理所有C語言的基本資料型
態,並回傳最大值及最小值。
void GMin(const void *pa, const void *pb, void *pOut, size_t n);
void GMax(const void *pa, const void *pb, void *pOut, size_t n);
pa及pb兩者為指向同一資料型態的輸入,pOut為輸出,n為資料大小
(byte)
49