为什么要用数据类型?
语言中之所以有数据类型,就是为了合理利用空间
数据类型的本质作用,就是合理的利用空间
数据类型的事例代码
#include#include void test01() { //C语言的基本类型char short int long float double //传智播客网站可以看黑马的视频教程 //char占一字节空间 char ch;//系统会给ch变量开辟一字节空间 //系统读取到char之后会在内存中找一个字节的空间 printf("sizeof(ch)=%dn",sizeof(ch)); //sizeof是用于测量大小的关键字 int num;//开辟4字节空间 printf("sizeof(num)=%dn",sizeof(num)); } int main(int argc, char *argv[]) { test01(); system("pause"); return 0; }
可以看出char所开辟空间的为一个字节,int所开辟的空间为4个字节
1B(字节)==8位b(二进制位)
1b只能存放0或1
1B就是8个0或1组成的
指针与内存
内存:内部存储器,是暂时存放数据的,断电就会丢失
内存是沟通CPU与硬盘的桥梁
内存有两个概念:
物理存储器和存储地址空间
物理存储器:就是实实在在存在的具体存储器芯片
存储地址空间:对存储器编码的范围
内存条上的颗粒组成了一个庞大的内存,程序员不关心内存如何构成,只关心如何使用,若想使用内存空间,就需要对内存的存储器进行编号,这个编号的范围就叫做地址。
CPU想要硬盘中读取数据,首先需要放到内存条当中,在把内存中的数据放入CPU
内存条都是几个G的大小,那么如何管理和操作呢?在进入地址之前,计算机会对内存中的空间进行编号,就像是外卖柜一样,如果箱子外没有相对应的编号,就会降低寻找的效率。所以对箱子进行了编号,内存中也是如此,内存内部的空间被分成一个个小格子并赋予了其标号。
外卖柜的每个标号对应着唯一的格子,在计算机中的内存也是如此。这样在使用格子的时候就可以轻松的找到这个格子。
内存的管理
将内存抽象成一个很大的一维字符数组
对内存中的每一个字节分配一个32位或64位的编号(分配32位还是64位与处理器是32位还是64位相关)
这个编号我们称之为内存地址(相当于房屋的门牌号)
比如:
char:占一个字节分配一个地址
int:占四个字节分配四个地址
float、struct、函数、数组等
那么如何得到这个号码呢?编号(地址):内存中每一个字节分配一个号码,这个号码就叫做地址 定义一个变量存放上面的号码,这样的变量叫做指针变量
如:
int num = 100;
因为是int类型的变量,就会给他开辟一个4个字节的空间。每一个字节都有一个号码,那int类型的变量应该就有4个号码。
事例代码
#include指针变量究竟是什么?#include void test02() { int num = 100; //取变量的地址用& printf("%pn",&num); //这里边有四个地址,那应该返回哪个地址? //答:对变量取地址,返回的是这个空间的起始地址 //所以printf打印的就是num 的起始地址 //需求:定义一个指针变量保存num的地址 //要保存一个变量的地址编号,首先用来保存的变量要是指针变量 //*和标识符结合就是表示指针变量: *p int *p = NULL; printf("sizeof(p)=%dn",sizeof(p)); //num的地址要与p建立关系 p = # printf("num = %dn",num); printf("*p = %dn",*p); //在定义的时候*p说明p是指针变量,不是普通变量 //在使用的时候*p表示取p保存的地址编号对应空间的内容 } int main(int argc, char *argv[]) { test02(); system("pause"); return 0; }
事例代码
#include#include void test03() { int num = 100; //指针变量的两种类型 //1.自身的类型:在指针变量定义的时候,将变量名涂黑,剩下啥类型,指针变量就是啥类型 //int *p = NULL; //将p涂黑,剩下int *,说明p就是int *类型的变量 //2.指向的类型:在指针变量定义的时候,将变量名和离它最近的*一起涂黑,剩下啥类型,指针变量指向的类型就是啥类型 //int *p = NULL; //p指向的类型就是int类型 //int **p = NULL; //此时p指向的类型就是int *类型 //指针变量指向的类型的作用,决定了指针变量所取空间内容的宽度,决定了指针变量+1跳过的单位跨度 //所取内容宽度:指针所保存的地址宽度 //单位跨度:指针所保存的地址+1所跨的字节数,char型跨一个,int型跨4个,以此类推 int *p = NULL; p = # //指针变量的跨度 printf("&num = %un",&num); printf("p = %un",p); printf("p = %un",p+1); //指针变量+1是进行一次关于数据类型的跨越 putchar(10); char *p1 = # printf("p = %un",p1); printf("p = %un",p1+1); //可以看到char类型的跨度只有1个字节 putchar(10); printf("p = %dn",*p);//num的值 putchar(10); //指针变量的宽度 //p保存的只是num的首地址,为什么可以把整个num取出来? int n = 0x01020304; //定义一个十六进制的数,十六进制的存放在linux和Windows系统中是倒着存储的(小端存储) //int类型具有四个字节,所以存放如下 //1 2 3 4 //0x04 0x03 0x02 0x01 int *p01 = &n;//保存地址宽度为4个字节 printf("*p01 = %#xn",*p01); //取出0x01020304 short *p02 = &n;//保存地址宽度为2个字节 printf("*p02 = %#xn",*p02); //取出0x0304 //只取出0x0102 //需要的地址宽度为2字节,同时要往后移动两个字节,所以用short+1 short *p03 = &n; p03 = p03+1; printf("*p03 = %#xn",*p03); //取出0x0102 //若使用char类型的话会出现如下结果 //取出的结果是0x020x01、 //造成这个结果的原因的是char是分别取出的两个字节 //而不是像short一样直接读取两个相邻字节的数据 char *p04 = &n; p04 = p04+2; printf("*p04 = %#x%#xn",*p04,*(p04+1)); } int main(int argc, char *argv[]) { test03(); system("pause"); return 0; }



