动态内存分配

来源:互联网 发布:强制写作软件 编辑:程序博客网 时间:2024/06/03 16:39

动态内存分配函数的原型都在头文件stdlib.h中声明。

malloc函数

malloc函数执行动态内存分配——malloc函数维护一个可用的内存池,当一个程序另外需要一些内存时,它就调用malloc函数,malloc函数从内存池中提取一块合适的内存,并向该程序返回一个指向这块内存的指针,这块内存此时并没有以任何方式进行初始化。

函数原型

void *malloc(size_t size);

返回类型——void*的指针类型

在C语言中,一个void*类型的指针可以转换为其他任何类型的指针。

所以,malloc函数不在乎用户请求的内存需要存储的是整数,浮点数,结构还是数组!

形参列表——size_t size

size_t是一个与机器相关的unsigned类型,其大小足以保证存储内存中对象的大小。

size就是malloc函数需要分配的内存字节(字符)的大小。

malloc函数所分配的一块连续的内存,同时,malloc实际分配的内存有可能比你请求的稍微多一掉。

  • 如果内存池中的可用内存可以满足这个需求,malloc就返回一个指向被分配的内存块起始位置的指针。
  • 如果内存池是空的,或者它的可用内存无法满足我们的请求,malloc函数会向操作系统请求,要求得到更多的内存,并在这块新内存上执行分配任务。
  • 如果操作系统无法向malloc函数提供更多的内存,malloc就返回一个NULL指针。

所以,对于每个从malloc返回的指针都要进行检查,确保它并非NULL!

#include <stdio.h>#include <stdlib.h>int main(){    int *pi;    pi = malloc(100);    if (pi == NULL)    {        printf("out of memory\n");        exit(1);    } else{        printf("hello!");    }    return 0;}

free函数

free函数执行动态内存的释放。当一块之前分配的内存不再使用时,程序调用free函数把它归还给内存池供以后之需。

函数原型

void free(void *pointer);

返回类型——void类型

形参列表——void *pointer

free函数的参数必须

  • 要么是NULL(向free函数传递NULL参数不会产生任何效果)。
  • 要么是从一个先前从malloc,calloc或realloc返回的指针。

注意

  • 传递给free函数一个指针,让它释放一块并非动态分配的内存可能导致程序立即终止或在晚些时候终止。
  • 释放一块内存的一部分是不允许的,动态内存分配的内存必须整块一起释放。
  • 不要访问已经被free函数释放的内存。
pi = malloc(10* sizeof(int));free(pi+5);

如上代码所示,我们首先申请了一块包含10个int型的内存块,但是我们只释放其中后五个int型内存块,这是错误的。

calloc函数

calloc函数也执行动态内存分配,但是和malloc函数相比,区别主要有二:

  • calloc在返回指向内存的指针之前把它初始化为0(主要区别)。
  • calloc请求内存数量的方式不同于malloc函数。

函数原型

void *calloc(size_t num_element , size_t element_size);

形参列表

calloc的参数包括两个:

  • 所需元素的数量——size_t num_element。
  • 每个元素的字节数——size_t element_size。

realloc函数

realloc函数用于修改一个原先已经分配的内存块的大小。

我们可以用realloc函数扩大或缩小一块内存。

如果用于扩大一个内存块,那么这块内存原先的内容依然保留,新增加的内存添加到原先内存块的后面,新内存并未以任何方法进行初始化。

如果用于缩小一个内存块,该内存块尾部的部分内存被拿掉,剩余部分内存的原先内容依然保留。

特别的,如果原先的内存块无法改变大小,realloc函数将分配另外一块正确大小的内存,并把原先那块内存的内容复制到新的块上。

函数原型

void realloc(void *ptr , size_t new_size);
0 0