第三章-数据类型

1. 数据类型分类

基本类型

整数类型 short int, int, long int , long long int
浮点数类型 float-单精度 double-双精度 long double
字符类型 char
布尔类型 _Bool
枚举类型 enum

 第三章-数据类型

通过sizeof 可以看到,每种类型在内存中预留的位置是多大。

#include   <stdio.h>

int main()

{
    printf("short int is %d
",sizeof(short int));
    printf("int length is %d
",sizeof(int));
    printf("long int is %d
",sizeof(long int));
    printf("long long int is %d
",sizeof(long long int));
    printf("float is %d
",sizeof(float));
    printf("double is %d
",sizeof(double));
    printf("_Bool is %d
",sizeof(_Bool));
    printf("long duoble int is %d
",sizeof(long double));
    return 0;
}

short int is 2
int length is 4
long int is 8
long long int is 8
float is 4
double is 8
_Bool is 1
long duoble int is 16

单位是字节

第三章-数据类型

signed:带符号,可以表示负数

unsigned:不带符号,只能表示0和正数

指针类型

构造类型

空类型

2. 数值类型的数值范围

比特位,CPU能读懂的最小单位,bit

内存中最小的寻址单位,Byte

1Byte = 8bit

第三章-数据类型

每个bit,只能存放0和1

1个Byte能够表示的最大的二进制数,为1111 1111。10进制表示为255。2**8 - 1

int 能存放4个字节的数字,4个字节就是4*8=32个bit,能存放的最大是32个1,10进制表示为 2**32-1 = 42949967295。也就数说int最大能存的数是42949967295,但是实际上不是这样的。

int 要分为带符号和不带符号。

如果是带符号,既可以表示正数,也可以表示负数。32个字节,第一个字节用来表示符号位,0表示正数,1表示负数。

那么能用的只剩下,31个位可以使用,

符号位为1的情况,31为能表示的数是31个1,2**31-1=2147483647。

符号位为0的情况,比较麻烦,计算机如何存放负数,通过补码的形式存放负数,负数的补码就不是二进制数了

计算机存放的都是补码。

补码是怎么来的呢?原码---反码---补码

7在计算机中的原码为 0 000 0111,最高位0表示正数,符号位,其余为数值位

7在计算机中的反码为 0 000 0111,正数的原码和反码一样。

7在计算机中的补码为 0 000 0111,正数的补码和反码一样。

-7在计算机中的原码为 1 000 0111,最高位1表示负数。

-7在计算机中的反码为 1 111 1000,最高位1表示负数,在原码的基础上,符号位不变,数值位为全部取反,0变成1,1变成0

-7在计算机中的补码为 1 111 1001, 最高位1表示负数,在反码的基础上,符号位不变,数值位的最后一位+1。

为什么要存放补码呢?是因为存放补码可以用+表示加和减,一举两得。

-7+7怎么表示呢?全是补码的相加

1 111 1001

0 000 0111

1 111 1112 ,舍弃最高位(符号位)进位后变成 000 0000,结果为0。

-7-7 怎么表示呢?也是补码的相加。-7 + (-7)

1 111 1001

1 111 1001

1 2222002 进位后变成  1 111 0010,这是补码的形式,如果变成反码为 1 111 0001 在变成 原码为 1 0001110 表示 -14。

计算机如果最高位字符位为1,表示为负数,需要将数值位-1,然后字符位取反,变成原码,就知道是负多少了。 

存放补码的意义是为了让减法变成加法来运算,比较快。不需要借位。算完的结果仍然是补码。

8个比特位,最小的负数是多少呢?负数的补码,0越多,数值越大,表示的负数就越小。

补码:1 000 0001---反码为---  1000 0000 ---原码为----1 111 1111 表示 -127

补码:1 000 0000---反码为----1 1111 1111 ---原码为 ---- 1 000 0000 表示 -128, 因为 1000 0000的二进制没有对应的任何真数,所以认为规定了为-128。

8个比特位,最大的整数是多少呢?正数色补码,1越多,数值越大,表示的正数越大。

补码 0 111 1111 --- 反码为 --- 0 111 1111 ---原码为---- 0 111 1111 表示 127。

补码 0 000 0000 --- 反码为 ---- 0 000 0000 ---原码为--- 0 000 0000 表示 0。

因此8个比特位的字符,反码能够表示带符号的范围为 [-128,127] 

https://blog.****.net/chenchao2017/article/details/79733278

第三章-数据类型

 第三章-数据类型

3. 字符和字符串

#include <stdio.h>

int main()
{

    char a = 'C';
    printf("%c = %d
",a,a);
    return 0;

}

root@ubuntu:/home/yanyanzhang/c_study# gcc test4.c -o test4 && ./test4
C = 67

67就是C在ASCII码表中对应的值

第三章-数据类型

字符类型就是一个特殊的整型,值都是对应到ASCII码表中的十进制值。

重点: char类型默认不是signed char,c语言并没有规定默认值,默认值是由编译系统自行决定,int等默认就是singed int。

举例说明:

#include <stdio.h>


int main()

{
    char height;
    height = 170;
    printf("my height is %d 
",height);    
    return 0;


}

root@ubuntu:/home/yanyanzhang/c_study# gcc test5.c -o test5 && ./test5
my height is -86 

身高竟然是-86,很奇怪,因为ubuntu系统的gcc指定了char默认是signed char,取值范围是-128,127,身高170超过了这个值,所以返回了怪怪的值-86。

将 char height;改为 unsigned char height;让取值范围变成0,255之间

root@ubuntu:/home/yanyanzhang/c_study# gcc test5.c -o test5 && ./test5
my height is 170 

字符串,声明 char 变量名[字符数量] ,申请了一个连续长度的空间。

#include<stdio.h>

int main()

{    
    char name[5] = {'z','h','z','z','z'};
    printf("name:%s
",name);
    return 0;

}

root@ubuntu:/home/yanyanzhang/c_study# gcc test6.c -o test6 && ./test6
name:zhzzz  没有出现乱码,c语言定义字符串的时候,要指定一个结束位, ,否则不知道从哪里结束

# TODO