C基础-内存的四驱模型

数据类型的本质

数据类型本质:一个固定大小连续的内存块。
数据类型的作用:分配内存空间大小

变量的本质

变量的本质:一段连续内存空间的别名

程序运行流程

1.操作系统把物理硬盘的代码 load到内存中(运行的是 .exe文件)
2.操作系统把C 代码分成四个区
3.操作系统找到main 函数的执行入口

内存四驱模型

在 c/c++ 中我们将运行时数据,分为四个区域分别是:栈区,堆区,数据区,代码区:
1.栈区:存放函数的参数值,局部变量的值等,由编译器自动分配释放。
2.堆区:存放的是一般我们自己malloc()或者new 出来的对象,一般由程序员分配释放, 若程序员不释放,程序结束时可能由 OS 回收。malloc对应free,new 对应 delete
3.数据区(静态区/全局区):存放全局变量、静态变量和常量字符串等等。 程序结束后由系统释放
4.存放函数体的二进制代码。

*1. 栈区
void change2(int * a){
    *a = 200;
}
void change1(int a){
    a = 200;
}

void main(){
    int  a = 100;
    int b = 10;
    change1(b);
    change2(&a);
    printf("change1 =%d,change2=%d", b,a);
    getchar();
}

//结果:change1 =10,change2=200

从结果上发现changge1()这个方法并没有改变b的值,而change2 () 改变了。

当执行 到 int a = 100; int b = 10时 栈区的结构时这样的


C基础-内存的四驱模型_第1张图片
image.png

当执行到change1(b)函数体内的时候,只是把变量a的值给了change1()函数的a.当该函数体执行完后,因为栈区时会自己回收的所以change1()的内存数据是会被清空的。所以b的值没有改变 b=10。
当执行到change2(&a);函数体内的时候,因为是传递的是a地址,然后通过地址修改a 的值,当
change2(&a)执行完 内存被清空后,a 的值已经发生改变了。


C基础-内存的四驱模型_第2张图片
image.png
*2. 全局区
char * getStr1(){
    char *p1 = "aaaaa";
    return p1;
}

char *getStr2(){
    char *p2 = "aaaaa";
    return p2;
}

void main(){
    char *p1 = NULL;
    char *p2 = NULL;

    p1 = getStr1();
    p2 = getStr2();

    printf("p1:%s , p2:%s \n", p1, p2);
    printf("p1:%d , p2:%d \n", p1, p2);

    getchar();

    // 打印结果:p1:aaaaa , p2:aaaaa  p1:10181068, p2 : 10181068
}

从打印结果可以看出p1 和p2 地址相同,指向的内容也相同
函数从main()函数入口执行,

 char *p1 = NULL;
 char *p2 = NULL;

对应的四驱模型如图:

编译器分别将变量p1,p2在栈区压栈,并给定初始值为NULL。
当执行getStr1()到函数体时如图:

当执行 p1 = getStr1()函数返回值赋给p1的时候,编译器会将getstr()函数在运行期其间申请的所有的栈区内存进行释放。内存四区如下:

同一样,当执行p2 = getStr2();语句时基本的内变化和p1相同,唯一不同的是编译器会对我我们的代码进行优化,p2指向的内存的值和p1相同时,编译器会只保留一个。这样内存四区如下

*3. 堆区
char *getMem(){

    char *p1 = NULL;
    p1 = (char *)malloc(sizeof(char)* 10);  //申请内存空间
    return p1;
}

void main(){
    
    char *tmp = NULL;
    tmp = getMem();
    strcpy(tmp, "aaabbb"); //向tmp做指向的内存空间中copy数据
    printf("tmp:%s.\n", tmp);
    getchar();

}

你可能感兴趣的:(C基础-内存的四驱模型)