目录

为什么要有动态内存分配 ?
我们已经掌握的内存开辟⽅式有:
- int val = 20;//在栈空间上开辟四个字节
- char arr[10] = {0};//在栈空间上开辟10个字节的连续空间
而开辟和释放所需要用到的函数就是malloc与free

C语⾔提供了⼀个动态内存开辟的函数:
void* malloc (size_t size);
想要多少字节就向内存申请多少个字节, 申请成功后会返回一共空间的起始地址,开辟失败会返回空指针(NULL)。
#include
- malloc(10 * sizeof(int));
- //申请10个整型的空间 - 40个字节
- if (p == NULL)
- {
- perror("malloc");
- return 1;
- }
- 冷知识:return 0 ;表示一共主函数的结束,也表示着一个正确的返回值,而在此时的return 1;表示的是一个返回失败的意思,或是说申请空间失败。
- return 1;也可以用return 2;或者return 3;表示,只要表示return 0;就行。
因为申请成功会返回起始地址,而返回的类型是void*所以我们要进行使用的时候需要进行转化,且我们要使用这个空间时得找一个相对因的变量指针进行存放空间起始地址。
int *p = (int*)malloc(10 * sizeof(int));
- int i = 0;
- for (i = 0; i <10; i++)
- {
- *(p + i) = i;
- }
-
- for (i = 0;i < 10; i++)
- { printf("%d",p[i]);
- return 0;
- }
- p+i表示地址,*(p+i)表示地址所指向的元素,所以这是给每个不同地址的不同的元素赋值。
- p[i]相当于*(p+i)

- int main()
- {
- int *p = (int*)malloc(10 * sizeof(int));
- if (p == NULL)
- {
- perror("malloc");
- return 1;
- }
- int i = 0;
- for (i = 0; i <10; i++)
- {
- *(p + i) = i;
- }
-
- for (i = 0;i < 10; i++)
- {
- printf("%d",p[i]);
- return 0;
- }
-
- return 0;
- }


- int main()
- {
- int *p = (int *)malloc(sizeof(int)*100);
- return 0;
- }
这就是开辟一百个int类型的元素
- int main()
- {
- int** p = (int**)malloc(sizeof(int) * 3);
- return 0;
- }
这也是开辟一维数组
开辟了三个空间,空间的类型是int**,用来存放int* 类型的元素
- int main()
- {
- int** p = (int**)malloc(sizeof(int) * 3);
- for (int i = 0; i < 3; i++)
- {
- p[i] = (int *)malloc(sizeof(int) *5);
- }
- return 0;
- }
开辟一个3*5的二维数组。
C语⾔提供了另外⼀个函数free,专⻔是⽤来做动态内存的释放和回收的,函数原型如下:
void free (void* ptr);
free函数 只能 ⽤来释放动态开辟的内存。
- int main()
- {
- int *p = (int*)malloc(10 * sizeof(int));
- if (p == NULL)
- {
- perror("malloc");
- return 1;
- }
- int i = 0;
- for (i = 0; i <10; i++)
- {
- *(p + i) = i;
- }
-
- for (i = 0;i < 10; i++)
- {
- printf("%d",p[i]);
- return 0;
- }
- free(p);//释放
- p = NULL;
- return 0;
- }
free(p);
p = NULL;
- p内存放的是申请的空间的起始位置。
- 而free只是把p指向的空间回收了。
- 而对于以上两段代码我们还得让p指针忘记申请空间的空间起始地址,不然p会变成野指针。