iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >C语言详细分析讲解内存管理mallocreallocfreecalloc函数的使用
  • 689
分享到

C语言详细分析讲解内存管理mallocreallocfreecalloc函数的使用

2024-04-02 19:04:59 689人浏览 八月长安
摘要

目录C语言内存管理一、动态空间申请二、动态空间的扩容三、释放内存C语言内存管理 malloc && realloc && free &&

C语言内存管理

malloc && realloc && free && calloc

c语言中为了进行动态内存管理,<stdlib.h>中提供了几个函数帮助进行内存管理。

我们知道,C语言中是没有c++中的容器或者说是python中list,set这些高级的数据结构的,我们一旦申请了一段内存空间以后这一段空间就归你了,比如我们举个例子,我们申请一个数组

int nums[100];

上面这段代码是完全可行的,但是我们现在在不知道想要申请多少空间的情况下呢?比如说下面这个例子

int func(int n){
	int nums[n];
}

我们发现出错了,连编译都过不了,为什么呢?因为这段空间是编译过程中确定的,我们不能在程序运行过程中申请一段不确定大小的空间。

所以我初学的时候就解决不了这个问题,我采取了一个笨办法,就是申请一个足够大的空间,反正用不完,我内存大咋滴了,也不是不可以,这个方法确实解决了我当初的问题不是嘛,但是现在我们有更好的办法,就是动态的空间申请。

一、动态空间申请

// 函数原型
void *malloc(unsigned int num);

在堆区分配一块指定大小的内存空间,用来存放数据。这块内存空间在函数执行完成后不会被初始化,它们的值是未知的。

int func(int n){
    int *nums = (int *)malloc(sizeof(int)*n);
    return 0;
}

这样我们就解决了不能进行动态的申请内存的问题了,我不知道有没有读者注意到malloc函数的返回类型是空指针类型,这样的话就需要我们进行强制类型转换,我们在上面的函数中是将其转换为了int指针类型,这样的话我们指向的空间就可以存放int值,也就是说我们申请了一个大小为n的int数组。返回空指针在一定程度上实现了泛型。我们也可以对这个数组进行初始化。

int func(int n){
    int *nums = (int *)malloc(sizeof(int)*n);
    memset(nums,0,sizeof(int)*n);
    return 0;
}

如果说malloc是没有初始化的内存申请,那么calloc就带初始化的内存申请

// 函数原型
void* calloc(unsigned int num,unsigned int size);

原本两步的工作现在一步就完成了

int func(int n){
    int *nums = (int *)calloc(n,sizeof(int));
    return 0;
}

这里还有一个问题就是,这个空间不够用了怎么办,比如我们用数组实现栈,或者是队列,我们不能说一直动态的申请,或者不够了就加,实际上像Python的list,他们在申请空间的时候都是多申请了一部分的,否则一会就加,一会就减,会影响效率,毕竟申请内存是需要向系统“打报告”的。

二、动态空间的扩容

我们之前申请的空间不够用了就需要扩容,我们可以用这个函数

// 函数原型
void *realloc(void *address,unsigned int newsize);

该函数重新分配内存,把内存扩展到 newsize。这里是扩展到多大,而不是扩展多少

int func(int n){
    int *nums = (int *)calloc(n,sizeof(int));
    nums = (int *)realloc(nums, sizeof(int)*n*2);
    return 0;
}

三、释放内存

当我们用完了这块动态内存空间时,我们需要手动释放,因为c没有智能的内存管理,只能依靠程序员自觉

// 函数原型
void free(void *address);

该函数释放 address 所指向的内存块,释放的是动态分配的内存空间。

int func(int n){
    int *nums = (int *)calloc(n,sizeof(int));
    nums = (int *)realloc(nums, sizeof(int)*n);
    free(nums);
    return 0;
}

这里我们需要注意两件事,第一件事,动态分配的内存必须释放,否则就会内存泄露,第二件事,结构体指针需要递归释放,务必释放干净

typedef struct node {
    int val;
    struct Node *next;
} Node;
void freeNode(struct Node *head){
    while(head){
        struct Node* temp=head->next;
        free(head);
        head = temp;
    }
}

更新一点知识,VLA变长数组,其实这么写在GCC中也是可以通过的

int n=10;
int nums[n];

我一开始看到这些代码也是很疑惑的,C语言到底支持不支持VLA变长数组啊,查了一点资料。

C90标准中并不支持VLA,C99开始支持VLA,很大的一个原因:FORTRAN中支持这种写法。C99中对对VLA有一些限制,比如变长数组必须是自动存储类型,也就是说,如果我上面两句放在函数外面就就不能通过编译了,这是因为在函数外面定义的是全局变量,此外,使用VLA不能对数组进行初始化,因为它的长度在运行时才能确定。

此外VLA并不是真正的变长,它实际上只是将数组的长度推迟到运行时确定而已,也就是说C90标准中,数组的长度必须在编译时期就知道,但C99支持VLA后,数组的长度可以推迟到运行时知道,但是,一旦长度确定,数组的长度就不能变了。

另外我在VC中编译并不能通过,在Clion中也不行,但是我LeetCode中提交的时候可以通过,也就是gcc其实是支持的。

我并不建议这么写,还是老老实实的malloc吧。

到此这篇关于C语言详细分析讲解内存管理malloc realloc free calloc函数的使用的文章就介绍到这了,更多相关C语言内存管理内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: C语言详细分析讲解内存管理mallocreallocfreecalloc函数的使用

本文链接: https://www.lsjlt.com/news/148362.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • C语言详细分析讲解内存管理mallocreallocfreecalloc函数的使用
    目录C语言内存管理一、动态空间申请二、动态空间的扩容三、释放内存C语言内存管理 malloc && realloc && free &&...
    99+
    2024-04-02
  • C语言与C++内存管理超详细分析
    目录一、内存1.1 内存四区1.2 使用代码证实内存四区的底层结构二、malloc 和 free2.1 malloc 和 free 的使用2.2 内存泄漏与安全使用实例与讲解三、ne...
    99+
    2024-04-02
  • C语言可变参数与内存管理超详细讲解
    目录概述动态分配内存重新调整内存的大小和释放内存概述 有时,您可能会碰到这样的情况,您希望函数带有可变数量的参数,而不是预定义数量的参数。C 语言为这种情况提供了一个解决方案,它允许...
    99+
    2023-01-02
    C语言可变参数 C语言内存管理
  • C语言详细讲解qsort函数的使用
    目录qsort1.int型2.float型3.struct型qsort 功能:Performs a quick sort.(快速排序)参数:void qsort( void *bas...
    99+
    2024-04-02
  • C语言超详细讲解字符串函数和内存函数
    目录字符串函数长度不受限制的字符串函数strlenstrcpystrcatstrcmp长度受限制的字符串函数介绍strncpystrncatstrncmp字符串查找以及错误报告str...
    99+
    2024-04-02
  • C++超详细分析讲解内联函数
    目录宏函数(带参数的宏)的缺点inline修饰的函数就是内联函数内联函数的特点宏函数和内联函数的区别宏函数(带参数的宏)的缺点 第一个问题:宏函数看起来像一个函数调用,但是会有隐藏一...
    99+
    2024-04-02
  • C语言超详细讲解getchar函数的使用
    目录一、getchar 函数二、缓冲区1、什么是缓冲区2、为什么要存在缓冲区3、缓冲区的类型4、缓冲区的刷新三、getchar 函数的正确使用1、getchar 的换行问题2、get...
    99+
    2024-04-02
  • 超详细分析C语言动态内存管理问题
    目录一、为什么存在动态内存的分配二、动态内存函数的介绍2.1 malloc和free2.2 calloc2.3 realloc三、常见的动态内存错误3.1 对NULL指针的解引用操作...
    99+
    2024-04-02
  • C++内存管理详细解析
    目录一、C++内存管理1、 new/delete表达式2、new/delete重载3、类内自定义allocator(per-class allocator) 二、多线程内存分配器1、...
    99+
    2024-04-02
  • C语言深入细致讲解动态内存管理
    目录为什么存在动态内存管理动态内存函数的介绍mallocfreecallocrealloc常见的动态内存错误对NULL指针的解引用操作对动态开辟空间的越界访问对非动态开辟内存使用fr...
    99+
    2024-04-02
  • C++详细讲解内存管理工具primitives
    目录primitivesnew 和 deleteplacement new重载 operator newper-class allocatorNew Handler=default,...
    99+
    2024-04-02
  • C语言深入讲解动态内存分配函数的使用
    目录一、malloc二、free(用于释放动态开辟的空间)三、calloc四、realloc五、常见的动态内存分配错误六、柔性数组局部变量和函数的形参向栈区申请空间 全局变量和sta...
    99+
    2024-04-02
  • C语言超详细讲解库函数
    目录1 返回整数的getchar函数2 更新顺序文件3 缓冲输出与内存分配4 库函数练习1 返回整数的getchar函数 代码: #include<stdio.h> ...
    99+
    2024-04-02
  • C语言内存分布与heap空间分别详细讲解
    目录内存分布变量内存4区模型开辟释放 heap 空间使用 heap 空间二级指针对应的 heap空间内存分布 程序没有加载到内存前,可执行程序内部已经分好3段信息,分别为代码区(te...
    99+
    2022-11-13
    C语言内存分布与heap空间 C语言内存分布 C语言heap空间
  • C语言内存操作函数使用示例梳理讲解
    目录一、memcpy()函数原型参数说明模拟算法使用示例二、memmove()函数原型参数说明模拟算法使用示例三、memset()函数原型参数说明使用说明使用示例四、memcmp()...
    99+
    2024-04-02
  • C语言详细分析浮点数在内存中的储存
    目录浮点数的储存格式初步了解深入探究E不全为0或不全为1E全为0E全为1浮点数的储存格式 初步了解 首先让我们通过一段代码来认识一下浮点型和整型的区别: int main() { ...
    99+
    2024-04-02
  • C语言函数超详细讲解上篇
    目录前言1、函数是什么?2、C语言中函数的分类2.1 库函数2.1.1 如何学会使用库函数2.1.2 自定义函数3、函数的参数3.1 实际参数(实参)3.2 形式参数(形参)4、函数...
    99+
    2024-04-02
  • C语言函数超详细讲解下篇
    目录前言函数的声明和定义函数声明函数定义举例简单的求和函数把加法单独改写成函数添加函数声明带头文件和函数声明静态库(.lib)的生成静态库文件的使用方法函数递归什么是递归?递归的两个...
    99+
    2024-04-02
  • C语言详细讲解常用字符串处理函数
    目录一、strlen()1. 函数原型:2. 手动实现:二、strcat()1. 函数原型:2. 手动实现:三、strcpy()1. 函数原型:2. 手动实现:四、strcmp()1...
    99+
    2024-04-02
  • C语言超详细讲解函数指针的运用
    目录前言计算器的例子回调函数转移表前言 前面我们学习了各种各样的指针类型,有些指针可以说是稀奇百怪,特别是函数指针,有些朋友可能觉得,函数指针有些多余,调用函数为什么要用指针调用,直...
    99+
    2024-04-02
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作