linux中几种管理内存的方式有:STL,new/delete,malloc/free,brk/sbrk,mmap/unmap
brk/sbrk:提供底层的内存分配函数
功能是共同维护系统的一个指针,主要用于对同类型的大块数据的动态存放,定义如下:
int brk(void *end_data_segment); // 通过移动指针分配空间,释放空间 void* sbrk(ptrdiff_t increment); // 分配内存空间,返回指定大小空间的地址
sbrk用法:第一次调用时,系统分配一大块空闲地址,把首地址返回,分配给一个指针phead,作为首地址不动;下一次调用时,返回当前位置的地址,分配给一个指针pnow,并把指针指向+increment的地方;
brk用法:对参数中pnow做绝对位置调整,调动指针左右移动,左移-释放空间,右移-分配空间
如果内存分配失败,二者都返回-1
注意:
1、每个进程可访问的虚拟内存空间为3G,在程序编译时,系统只分配并不大的数据段空间,称为1页,共4096字节,如果这块空间不够,就使用sbrk函数将数据段的下界移动,获得新的空间,这也是malloc的原理。
2、phead和pnow之间的内存空间才是合法内存,在没有分配空间的地方存取数据会发生段错误,在合法内存之外存取数据会发生越界,导致不可预知的错误。
例:将1-10000之间的所有素数存放到缓冲,并输出
#include <stdio.h> #include <unistd.h> // 使用brk/sbrk,需要使用这个头文件 int main() { //存放数据 int i = 2; int* phead; // 指向首位置 int* pnow; // 指向当前指针位置 pnow = sbrk(0); // 先分配空闲区域 phead = pnow; // 固定首位置不变 for(i=2; i<10000; i++) { if(isPrime(i)) // 该函数用于判断是否是素数 { brk(pnow+1);// 分配4个字节 *pnow = i; // 存入数据 pnow = sbrk(0); // 指向系统指针上次移动到的那个位置 } } //打印数据 pnow = phead; // 从头打印 while(pnow!=sbrk(0)) { printf("%d\n",*pnow); pnow++; } brk(phead); // 释放空间 }