C语言内存四大区域几点总结
2017-07-26 19:58
113 查看
未初始化全局变量默认值为0,未初始化局部变量一般默认值为随机数,但有的编译器也为0。
一、栈:
栈遵循后进先出,栈的大小由编译器决定。一般来说,默认栈的大小为1M,所以如果变量分配内存过大可能会造成栈溢出。比如: 定义一个数组长度为200M,
double a[1024*1024*200]如果编译器栈大小不够的话会造成溢出。
栈不同于堆,栈用完立即回收,所有局部变量都存放在栈中。
如下程序会一直进行分配与回收,该程序运行起来会很消耗CPU
while(1) { double arr[1024*200]; }
计算机中计算是由CPU来完成的,而计算结果保存在内存中,所以a+1=2 这种赋值方式是错误的。
二、堆区:
内存分配函数有:malloc calloc realloc分配的内存不会自动释放,需要配合free()使用。如果执行内存分配以后不释放,则会造成内存泄漏,严重的话会把内存分配完导致计算机崩溃。
用指针写for循环:
#include <stdio.h> #include <stdlib.h> void main() { int *p = (int *) malloc(sizeof(int)*10); int num=0; int *px=p; for(;px<p+10;px++) { *px=num; printf("%p\n,%d\n",px,*px); num++; } }
注意:
指针本身是一个变量,他存放在栈区(&p)
指针所指向的地址存放在堆区(p)
三、代码段:
存放函数的执行代码。例如:函数名(函数的入口地址),以及函数的参数。常量位于代码区,代码区都是只读的。
1、函数指针的定义:
把函数名挖掉,用 (*p) 代替。例如:void (*pfuc) ( 参数) =fuc; (fuc为函数名)
间接调用: pfuc(参数);
以上两个式子等价于:直接调用
fuc(参数);
2、关于const
#define N 10 宏定义有CPU产生,N不可取地址const修饰的数据是一个伪常量(只读常量),只是限定编译器尽量不修改它修饰的变量,其实是可以间接修改的。
- const在前面 const int nValue; //nValue是const const char *pContent; //*pContent是const, pContent可变 const char* const pContent; //pContent和*pContent都是const const在后面,与上面的声明对等 int const nValue; //nValue是const char const * pContent; //*pContent是const, pContent可变 char* const pContent; //pContent是const,*pContent可变 char const* const pContent; //pContent和*pContent都是const
const int num=10; int data[10]; //不合法的,因为num是个伪常量(只读常量)
解析:常量是被编译器放在内存中的只读区域,当然也就不能够去修改它。而”只读变量”则是在内存中开辟一个地方来存放它的值,只不过这个值由编译器限定不允许被修改。C语言关键字const就是用来限定一个变量不允许被改变的修饰符(Qualifier)。上述代码中变量n被修饰为只读变量,可惜再怎么修饰也不是常量。而ANSI C规定数组定义时长度必须是”常量”,”只读变量”也是不可以的,”常量”不等于”不可变的变量”。但是在C++中,局部数组是可以使用变量作为其长度的。
间接修改const修饰数据的值:
所以可以用一个指针指向num,然后就可以通过指针来修改num的值了。
#include <stdio.h> int main() { const int num=10; int *p=(int *)# *p=100; printf("%d",num); }
四、关于静态变量,局部变量,全局变量,外部变量:
对于局部变量:未初始化也叫定义,所以不能对一个变量申明两次。
对于全局变量:定义=申明+赋值。所以如果没有初始化只能叫做申明,所以可多次申明同一个变量,虽然没有什么意义。
静态变量和局部变量的区别:静态变量被限定在本C文件中才可以使用。
全局变量和外部变量,如下:
//test1.c int a=2; //test2.c #include <stdio.h> //int a; 函数体外部只需要申明即可以,但是不能给a赋值,否则就是重定义 void main() { extern int a; //在函数体内部调用其他文件的全局变量,需要用extern申明 printf("%d",a); }
参数入栈顺序:从左往右
相关文章推荐
- cocos2d-x开发的几点总结
- 2014亚洲区域赛西安站总结
- 如何做好外包项目验收?我总结的几点建议
- 关于2410上LCD移植方面的几点总结(含触摸屏)——转载
- 关于left join 的几点总结
- c/c++中内存区域划分大总结
- udhcp的几点总结
- 求职的几点总结
- 总结几点关于做互联网产品的思路
- 自适应XAML布局经验总结 (四)区域布局设计模式
- SQL语句效率问题的几点总结
- 设计模式大杂烩(24种设计模式的总结以及学习设计模式的几点建议)
- 几点总结
- 使用CHotKeyCtrl的几点总结
- [原创]JavaScript 与 CSS 兼容 Firefox 的几点总结
- C/C++中内存区域划分大总结
- Linux用户空间与内核空间数据传递的几点理解和总结
- 关于premiere中遮罩的几点总结 数媒0802 宋志超
- GDI+学习及代码总结之------画线、区域填充、写字
- 有关位图的几点总结