Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

What are the common errors in dynamic memory allocation in C language programming?

2025-01-15 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

Shulou(Shulou.com)06/03 Report--

This article introduces the knowledge of "what are the common mistakes in dynamic memory allocation in C language programming". In the operation of actual cases, many people will encounter such a dilemma. Next, let the editor lead you to learn how to deal with these situations! I hope you can read it carefully and be able to achieve something!

Catalogue

Why is there dynamic memory allocation?

I. dynamic memory function

1.malloc and free functions

2.calloc function

3.realloc function

Second, common mistakes

1. Dereferencing the NULL pointer

two。 Cross-border access to dynamic opening up space

3. Use the free function for non-dynamic development

4. Use free to free up a piece of dynamic memory to open up a portion of memory

5. Release the same space many times

6. Dynamically open up memory and forget to release

Why is there dynamic memory allocation?

The ways we have mastered memory development are as follows

Int axi10ramp / open 4 bytes char arr [10] = {0} on stack space; / / open 10 bytes contiguous space on stack space

The above approach to opening up space has two disadvantages:

1. The size of the space is fixed.

two。 When an array is declared, it must specify the length of the array, and the memory it requires is allocated at compile time.

But the need for space is not just the case mentioned above. Sometimes the amount of space we need can only be known when the program is running, so the above methods can not meet the needs. Let's introduce a solution: dynamic memory allocation.

I. dynamic memory function

(picture from bit Employment course)

When a computer is in use, there are three areas: the common stack area, which is used to store local variables and function form parameters; the static area, which is used to store static areas and global variables; and the last stack area, which we use for dynamic memory allocation. To learn dynamic memory allocation, you must master the following four functions:

1.malloc and free functions

The malloc function declaration:

Void*malloc (size_t size); / / size_t is unsigned int

This function requests a continuously available space from memory and returns a pointer to that space. The notes are as follows:

1. If the opening is successful, return a pointer to the open space

two。 If opening fails, return a NULL pointer

(because it is a NULL pointer, assert is often checked for malloc functions.)

3. The return type is void*, so the type of space opened by the malloc function needs to be decided by the user.

4. If the behavior of size=0,malloc depends on the specific compiler

Free function declaration

Void free (void*ptr)

The free function is used to free up space for dynamic development. Note that:

1. If the space pointed to by the parameter ptr is not dynamically opened up, then the behavior of the free function is unknown

two。 If ptr is a null pointer, the free function does nothing

Examples of actual combat:

# include#include//malloc and free function header file int main () {int*p= (int*) malloc (40) / / the space out of malloc is of uncertain type, so you need to force a type by yourself / / here we convert it to int*, and maintain this space by integer pointers / / then there will be 4 bytes as an element, 40 bytes, which can fill 10 int elements if (p = = NULL) {return-1. } / / if no return value is returned, it means int I = 0; for (I = 0 * * I)

< 10;i++) { *(p + i)=i;//对开辟空间进行赋值操作 } free(p);//用完之后不需要了,用free函数释放p所指向的空间(40个字节全部释放掉,还给操作系统) p = NULL;//由于p存储的是开辟空间的地址,即使空间还给了操作形态,但p还是可以找到这块空间,这是非常危险的,所以我们用一个空指针赋给p return 0;}2.calloc函数 calloc函数也是用来动态内存分配的,函数声明如下 void*calloc(size_t num,size_t size) 该函数功能是为num个大小为size的元素开辟一块空间,并且把空间的每个字节都初始化为0 它与malloc函数的区别只是在返回地址前会把申请空间里的每个字节都初始化为0 代码如下(示例): #include#include//calloc函数头文件#include//strerror函数头文件#include//errno头文件int main(){ int*p = (int*)calloc(10, sizeof(int));//开辟10个大小为int型的空间 if (p == NULL)//calloc函数也有可能开辟空间失败,需要进行检验 { printf("%s\n", strerror(errno));//errno是错误码,strerror会把错误码转换成相应的错误信息 return -1; } int i = 0; for (i = 0;i < 10;i++) { printf("%d ", *(p + i));//会打印10个0(calloc会自己初始化为0) } free(p); p = NULL; return 0;}3.realloc函数 realloc函数是在已有空间不够的情况下,进行追加申请空间的函数,其声明如下: void*realloc(void*memblock,size_t size); realloc函数是为了让动态内存管理更加灵活,有时候我们发现之前申请的空间过少了,或者过大了,我们可以用realloc函数来进行增减,它的注意点如下: 1.ptr是要调整的内存地址 2.size是调整之后新的大小 3.返回值是调整后的内存起始位置 4.该函数在调整原先内存大小的基础上,还会将原来内存的数据复制到新空间 5.realloc函数在调整内存空间存在两种情况 关于4和5解释如下: 假设我们现在追加1倍空间

The first kind: as shown in the picture above, red is the space we have opened up, and blue is the space that other programs are using, and because we want to open up the space must be physically continuous, we cannot use the blue part. what if the blank space in the middle is not twice as much as the original space?

We will find another place with enough space to open up twice the original space, and copy the data in the original space to the new space, and the function returns the address of the new space.

The second kind: this is relatively simple, the original space behind is enough to open up a 1 times the space, we can directly open up.

The function directly returns the first address of the previous space.

Of course, realloc functions, like malloc and calloc functions, may fail to open up space, so you still need to verify that null pointers are returned.

# include#include//malloc and free function header file int main () {int*p= (int*) malloc (40); / / Open up a space of 10 int size int I = 0; for (I = 0 int*ptr I < 10 int*ptr I +) {* (p + I) = I Bing / assign to the open space} int*ptr = realloc (p, 20 * sizeof (int)) / / attention! Here 20*sizeof (int) is the new size / / for example, I only have 10 now, I need 20, and I'm short of 10. But instead of writing 10, we will write the new size 20 if (ptr! = NULL) {p = ptr;} for (I = 10 * (p + I) = I) / a pair of newly opened spaces assigned {* (p + I) = I;} for (I = 0 + I < 20). Printf +) {printf ("% d", * (p + I)); / / print 0-19} free (p); p = NULL; return 0;} II. Common error 1. Dereferencing the NULL pointer

The code is as follows (example):

# include#includeint main () {int*p = (int*) malloc (20); * p = 0 free / dereferencing p and assigning it to 0 free (p); return 0;}

Functions such as malloc may fail when opening up space. If they fail, they will return a null pointer. There must be something wrong with dereferencing and assigning values to the null pointer directly.

So we still have to do pointer testing here.

The code is as follows (example):

# include#includeint main () {int*p = (int*) malloc (20); if (p==NULL) {return-1; / / if returned, open a failed termination program. If it is not returned, you can do the following operation: * p = 0 free (p) / dereference to p and assign it to 0 free (p); return 0;} 2. Cross-border access to dynamic opening up space

The code is as follows (example):

# include#includeint main () {int*p = (int*) malloc (200); / 200Bytes that is 50 int if (p = = NULL) {return-1;} int I = 0; for (I = 0 X I < 60 free I +) {* (p + I) = I;} free (p) P = NULL; return 0;}

At first glance, this code looks fine, but if you look closely, you will find that malloc opens up 200 bytes of space, that is, 50 int types, and your for loop assignment can only be 50 times at most. 60 times of your loop must be out of bounds, and it is appropriate to report an error here.

3. Use the free function for non-dynamic development

The code is as follows (example):

# include#includeint main () {int a = 10; int*p = & a; free (p); p = NULL;}

Here int creates a, then assigns the address of a to p of type int*, and then free drops p. This kind of operation is also bound to report an error. The local variable p is on the stack, and the free function is for the stack area.

4. Use free to free up a piece of dynamic memory to open up a portion of memory

The code is as follows (example):

/ / use free to free a piece of dynamic memory to open up part of the memory # include#includeint main () {int*p = (int*) malloc (10 * sizeof (int)); if (p = = NULL) {return-1;} / use int I = 0; for (I = 0 Free +) {* paired + = I;} / / release free (p); p = NULL;}

What's wrong with the code here? Let's draw a picture and it will be clear at a glance.

At first p is in the position of the image above, but with the for loop, the position of p points back and forth to the position of the image below.

At this time, p no longer points to the position where the space was opened up, and it is obviously not appropriate for you to release it with free at this time.

5. Release the same space many times

Let's first look at two pieces of code:

# include#includeint main () {int*p = (int*) malloc (40); if (p = = NULL) {return-1;} free (p); free (p);} # include#includeint main () {int*p = (int*) malloc (40); if (p = = NULL) {return-1 } free (p); p = NULL; free (p);}

Both pieces of code are released multiple times for the same piece of space, but the first piece of code will report an error and the second will not.

The explanation is as follows:

In the first piece of code, you have released the space pointed to by p, there is nothing in the space, but p still points to that space, so you will definitely report an error if you release the space that does not belong to you again.

In the second section of the code, you release the space pointed to by p, then assign a value to p with a null pointer, and then release a null pointer. We know that the free null pointer does nothing, so it won't report an error.

6. Dynamically open up memory and forget to release

For dynamic memory opening and forgetting to release, there are two ways to reclaim the space applied for on the heap:

1. You free it yourself.

two。 When the program exits, the system automatically reclaims

Let's look at a piece of code first.

# include#includeint main () {int*p = (int*) malloc (40); if (p = = NULL) {return-1;} getchar (); return 0;}

The code we do not use free to release memory, and in the middle there is getchar has been waiting to receive characters, for example: if you go to the toilet or do other things, getchar has not received the characters, the program has not been over, then we use p to open up space during your toilet has been occupied, the space system has no way to do other meaningful things. And rise to the company level in the future: the program we write may be running 24 hours a day, so in this case, you don't lose memory without free, you don't have to recycle it, and the impact on overall efficiency is very great.

This is the end of the content of "what are the common mistakes in dynamic memory allocation in C language programming?" Thank you for reading. If you want to know more about the industry, you can follow the website, the editor will output more high-quality practical articles for you!

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Development

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report