初步理解malloc与指针
malloc
void* malloc (size_t size);
分配 size 字节大小的空间,返回该空间首部的地址。
新分配的空间上的内容没有被初始化,仍然具有不确定的值。
如果 size 的大小为0,返回值取决于特定的库的实现(有可能是空指针,也有可能不是),但是返回的地址不应该被解引用。
分配成功返回首地址,分配失败返回NULL
头文件:<stdlib.h>
https://cplusplus.com/reference/cstdlib/malloc/?kw=malloc
为什么要有malloc?
malloc 和指针密切相关,我们知道指针是指向地址的变量,比如说有以下代码
#include <stdio.h> int main(void) { int n = 0; int* p = &n; return 0; }
内存中有个变量是 n,它的值为0,内存中还有个变量是 p,它的值为 n 的地址。注意,指针变量本身也在内存中占据一块空间,你可以再定义一个变量 p2 来指向这个指针的地址,这个变量 p2 就是所谓的二级指针,即指针的指针,你可以一直套下去,三级指针,四级指针…
#include <stdio.h> int main(void) { int n = 0; int* p = &n; int** p2 = &p; return 0; }
那么为什么需要 malloc 呢?
道理很简单,指针变量的值是地址,地址对应着一块空间,没有空间,指针就不知道指向哪里,于是 malloc 起作用了,malloc可以分配一块空间,使指针指向这块空间开头的地址。并且,对于指针我们常常还伴有解引用操作,去操作某个地址上的值,如果这个地址不明确,这个指针不知道指向哪里,我们就没办法完成解引用的操作。
如果指针变量的值不是一个确定空间的地址,那么它就是野指针,我们要尽量避免野指针。
我在学习链表的过程中使用 malloc 时常常对以下代码感到困惑
LNode* p; p->data = 100;
这样的代码是错误,p 是一个链表结点指针,你想要让 p->data 的值为100,可 p 根本不知道指向哪里,它就是个野指针,你再对这个不知道指向哪里的 p 进行操作,这当然不可以。我们需要让 p 指向一个实实在在的地方。
//方式一 LNode n; LNode* p = &n; p->data = 100; //方式二 LNode* p = (LNode*)malloc(sizeof(LNode)); p->data = 100;
方式一是定义一个结点变量 n,系统会自动给它开辟空间,方式二是我们用 malloc 开辟一块空间,不管怎样,我们都是为了让指针指向一块确定的空间
其实上面的代码就和下面的代码一样
#include <stdio.h> int main(void) { int* n; *n = 1; return 0; }
同样的问题,n 不知道指向哪里
free
void free (void* ptr);
free 与 malloc 函数是配对使用的
首先一定要保证 free 函数中的参数 ptr 是指向 malloc 开辟的空间
其次,free 过后,ptr 可能仍然指向原来的地址,所以我们一般还需要令 ptr = NULL;
free 过后,我们就不能再使用这个 ptr 了,即使它仍指向原来的地址
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
· 三行代码完成国际化适配,妙~啊~