C语言跟内存分配方式程序员
(1) 从静态存储区域分配。内存在程序编译的时候就已经分配好,这块内存在程序的整个运行期间都存在。例如全局变量,static变量。数组
(2) 在栈上建立。在执行函数时,函数内局部变量的存储单元均可以在栈上建立,函数执行结束时这些存储单元自动被释放。栈内存分配运算内置于处理器的指令集中,效率很高,可是分配的内存容量有限。函数
(3)从堆上分配,亦称动态内存分配。程序在运行的时候用malloc或new申请任意多少的内存,程序员本身负责在什么时候用free或delete释放内存。动态内存的生存期由咱们决定,使用很是灵活,但问题也最多spa
C语言跟内存申请相关的函数主要有 alloca,calloc,malloc,free,realloc,sbrk等.翻译
其中alloca是向栈申请内存,所以无需释放. malloc分配的内存是位于堆中的,而且没有初始化内存的内容,所以基本上malloc以后,调用函数memset来初始化这部分的内存空间.指针
calloc则将初始化这部分的内存,设置为0. 而realloc则对malloc申请的内存进行大小的调整.申请的内存最终须要经过函数free来释放. 而sbrk则是增长数据段的大小;对象
malloc/calloc/free基本上都是C函数库实现的,跟OS无关.C函数库内部经过必定的结构来保存当前有多少可用内存.若是程序malloc的大小超出了库里所留存的空间,那么将首先调用brk系统调用来增长可用空间,而后再分配空间.free时,释放的内存并不当即返回给os,而是保留在内部结构中. 能够打个比方: brk相似于批发,一次性的向OS申请大的内存,而malloc等函数则相似于零售,知足程序运行时的要求.这套机制相似于缓冲.内存
使用这套机制的缘由: 系统调用不能支持任意大小的内存分配(有的系统调用只支持固定大小以及其倍数的内存申请,这样的话,对于小内存的分配会形成浪费; 系统调用申请内存代价昂贵,涉及到用户态和核心态的转换. 函数malloc()和calloc()均可以用来分配动态内存空间,但二者稍有区别。资源
malloc()函数有一个参数,即要分配的内存空间的大小:get
Void *malloc(size_t size);
calloc()函数有两个参数,分别为元素的数目和每一个元素的大小,这两个参数的乘积就是要分配的内存空间的大小:
void*calloc(size_t numElements,size_t sizeOfElement);
若是调用成功,函数malloc()和calloc()都将返回所分配的内存空间的首地址。
malloc() 函数和calloc()函数的主要区别是前者不能初始化所分配的内存空间,然后者能。若是由malloc()函数分配的内存空间原来没有被使用过,则其中 的每一位可能都是0;反之,若是这部份内存空间曾经被分配、释放和从新分配,则其中可能遗留各类各样的数据。也就是说,使用malloc()函数的程序开 始时(内存空间尚未被从新分配)能正常运行,但通过一段时间后(内存空间已被从新分配)可能会出现问题。
calloc() 函数会将所分配的内存空间中的每一位都初始化为零,也就是说,若是你是为字符类型或整数类型的元素分配内存,那么这些元素将保证会被初始化为零;若是你是 为指针类型的元素分配内存,那么这些元素一般(但没法保证)会被初始化为空指针;若是你是为实数类型的元素分配内存,那么这些元素可能(只在某些计算机 中)会被初始化为浮点型的零。
malloc() 函数和calloc()函数的另外一点区别是calloc()函数会返回一个由某种对象组成的数组,但malloc()函数只返回一个对象。为了明确是为一 个数组分配内存空间,有些程序员会选用calloc()函数。可是,除了是否初始化所分配的内存空间这一点以外,绝大多数程序员认 为如下两种函数调用方式没有区别:
calloc(numElements ,sizeOfElement);
malloc(numElements *sizeOfElement) ;
须要解释的一点是,理论上(按照ANSIC标准)指针的算术运算只能在一个指定的数组中进行,可是在实践中,即便C编译程序或翻译器遵循这种规定,许多C 程序仍是冲破了这种限制。所以,尽管malloc()函数并不能返回一个数组,它所分配的内存空间仍然能供一个数组使用(对realloc()函数来讲同 样如此,尽管它也不能返回一个数组)。
总之,当你在calloc()函数和malloc()函数之间做选择时,你只需考虑是否要初始化所分配的内存空间,而不用考虑函数是否能返回一个数组。
当程序运行过程当中malloc了,可是没有free的话,会形成内存泄漏.一部分的内存没有被使用,可是因为没有free,所以系统认为这部份内存还在使用,形成不断的向系统申请内存,是的系统可用内存不断减小.可是,内存泄漏仅仅指程序在运行时,程序退出时,OS将回收全部的资源.所以,适当的重起一下程序,有时候仍是有点做用.