当前位置:网站首页>动态内存管理及柔性数组
动态内存管理及柔性数组
2022-07-26 05:17:00 【终成大师的康康】
今天我想为大家讲讲动态内存开辟及柔性数组的相关知识。
动态内存管理:
动态内存管理主要涉及:malloc、calloc、realloc和free函数。主要把这四个函数学会并加以灵活的应用,拿着方面的知识点就算基本掌握了,话不多说现在开始。
首先是malloc函数:
void *malloc( size_t size );
malloc的类型的void*,所以在开辟动态内存之前我们要先思考我们要创建的数据类型,并把malloc的类型强行转换成我们需要的类型。它的参数是我们需要的字节个数。现在我为大家举例,例如我们需要创建10个整型的数据:

但是动态内存的开辟,如果程序员不进行内存的回收可能会出现内存泄漏的问题,那么如何回收开辟的内存呢?这时我们需要用到free函数。
这是free函数的声明:
void free( void *memblock );使用非常简单,参数就是我们动态开辟的地址。注:开辟的内存地址最后要置成空指针。
free(str);
str = NULL;现在再来介绍calloc函数,它和malloc区别就是会对内存开辟中的数值进行初始化。
这是calloc的初始化:
void *calloc( size_t num, size_t size );我们依旧用创建10个整形的例子:

动态内存的开辟讲究的是动态,那么该如何实现动态呢?
这是realloc函数派上了用场:
void *realloc( void *memblock, size_t size );
现在我要将创建的10个整形扩展到20个整形,使用方式如下:

其实用realloc函数开辟内存的方式有两种:


现在我们来谈一谈动态内存开辟常见的几个问题:
1.非动态内存的空间用free释放。
2.用free释放部分的动态内存。
3.对动态开辟的空间进行越界访问。
4.对NULL指针进行解引用操作(开辟的地址没有进行是否为null指针的判断)
5.对同一块动态内存进行多次释放。
6.开辟的动态内存没有进行内存的释放。
现在我们来介绍几个经典的面试题:
void GetMemory(char *p) {
p = (char *)malloc(100);
}
void Test(void) {
char *str = NULL;
GetMemory(str);
strcpy(str, "hello world");
printf(str);
}请问运行Test 函数会有什么样的结果?
1.str传进GetMemory想要接收p的地址,已知形参是实参的一份临时拷贝,对形参的修改不会影响实参,故str依旧是空指针,strcpy将hello world拷贝到空指针去程序报错。
2.动态内存开辟没有释放空间,造成内存泄漏。
char *GetMemory(void) {
char p[] = "hello world";
return p; }
void Test(void) {
char *str = NULL;
str = GetMemory();
printf(str);
}请问运行Test 函数会有什么样的结果?
1.str接收到了动态内存开辟的p的地址,但是出了函数以后,由于p占据的是栈空间的地址,p的空间将会被操作系统回收,所以失去了访问p空间的权限。造成了野指针的使用。
2.不会打印出hello world。
void GetMemory(char **p, int num) {
*p = (char *)malloc(num);
}
void Test(void) {
char *str = NULL;
GetMemory(&str, 100);
strcpy(str, "hello");
printf(str);
}请问运行Test 函数会有什么样的结果?
1.会打印出hello
2.造成内存泄漏。
void Test(void) {
char *str = (char *) malloc(100);
strcpy(str, "hello");
free(str);
if(str != NULL)
{
strcpy(str, "world");
printf(str);
}
}请问运行Test 函数会有什么样的结果?
1.空间已经被释放再将world拷贝到指针所指向的空间中造成野指针使用的问题。
修改方法:将free放在最后。
柔性数组:
typedef struct st_type
{
int i;
int a[];//柔性数组成员
}type_a;柔性数组的概念非常简单,就是结构体中最后一个结构体变量是个大小不确定的数组,我们用malloc为结构体开辟空间(开辟的大小大于结构体的大小以适用于数组)。结构体的大小与数组大小无关(数组大小不计)。数组的前面至少有一个结构体其他成员!
int i = 0;
type_a *p = (type_a*)malloc(sizeof(type_a)+100*sizeof(int));
//业务处理
p->i = 100;
for(i=0; i<100; i++) {
p->a[i] = i; }
free(p);有人思考可以将结构体中的数组换成一个指针,再为这个指针开辟一个动态内存。那么问题来了,这样做会让内存碎片化,其次要进行两次free空间的释放,容易造成内存泄漏,不方便用户的使用。最后就是减慢运行速度:每开辟一次空间就要向操作系统申请权限,操作系统同意了才会进行动态内存的开辟。
所以柔性数组的优势显而易见啦!
好了到这就已经把这一章的知识点梳理完毕了,如果不对的地方请指正,康康一定会虚心接受!
边栏推荐
- 学生如何申请免费IDEA
- Trend of the times - the rise of cloud native databases
- Do you really understand fiddler, a necessary tool for testing?
- SAP report development steps
- Black eat black? The man cracked the loopholes in the gambling website and "collected wool" for more than 100000 yuan per month
- ThreadLocal transfer between parent and child threads in asynchronous
- JVM Lecture 5: how to deal with peak push of vertical and horizontal data
- MySQL basic learning
- C language force buckle question 42 of rain. Four methods - violence, dynamic planning, stack, double pointer
- ALV程序收集
猜你喜欢

Leetcode linked list problem - 206. reverse linked list (learn linked list by one question and one article)

Recommend 12 academic websites for free literature search, and suggest to like and collect!

TZC 1283: simple sort Bubble Sort

Basic methods of realizing licensing function in C language

Go-Excelize API源码阅读(六)—— DeleteSheet(sheet string)

手把手教你用代码实现SSO单点登录

JVM Lecture 5: how to deal with peak push of vertical and horizontal data

Full analysis of domain name resolution process means better text understanding

Security permission management details

Use flutter to adjust a color filter for the picture of my little sister
随机推荐
如何优雅的复现YOLOv5官方历程(二)——标注并训练自己的数据集
【Leetcode】493. Reverse Pairs
Nacos 介绍和部署
Mysql优化
Use flutter to adjust a color filter for the picture of my little sister
ThreadLocal transfer between parent and child threads in asynchronous
YOLOv5执行全过程----目录
How to conduct test case review
SAP report development steps
Embedded development notes, practical knowledge sharing
Map making of environmental impact assessment based on remote sensing interpretation and GIS technology
C语言详解系列——函数的认识(4)函数的声明与定义,简单练习题
NPM operation instruction
LeetCode链表问题——203.移除链表元素(一题一文学会链表)
no networks found in /etc/cni/net.d
Install nccl \ mpirun \ horovod \ NVIDIA tensorflow (3090ti)
Flex layout principle and common parent elements
Lesson 2 getting to know slam for the first time
Do you really understand fiddler, a necessary tool for testing?
TZC 1283: simple sort Bubble Sort