修剪时可以重新分配失败(返回NULL)吗? [英] Can realloc fail (return NULL) when trimming?

查看:97
本文介绍了修剪时可以重新分配失败(返回NULL)吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果执行下一个操作:

int* array = malloc(10 * sizeof(int));

我使用realloc:

and them I use realloc:

array = realloc(array, 5 * sizeof(int));

在第二行(并且只有第二行),它可以返回NULL吗?

On the second line (and only it), can it return NULL?

推荐答案

是的. realloc()上没有实现保证,并且即使收缩也可以返回不同的指针.

Yes, it can. There are no implementation guarantees on realloc(), and it can return a different pointer even when shrinking.

例如,如果特定的实现对不同的对象大小使用不同的池,则realloc()实际上可以为较小的对象在池中分配一个新块,而为较大的对象释放该池中的块.因此,如果较小对象的池已满,它将失败并返回NULL.

For example, if a particular implementation uses different pools for different object sizes, realloc() may actually allocate a new block in the pool for smaller objects and free the block in the pool for larger objects. Thus, if the pool for smaller objects is full, it will fail and return NULL.

或者可能只是简单地决定移动块就更好了

Or it may simply decide it's better to move the block

我只是使用以下程序通过glibc获取实际分配的内存大小:

I just used the following program to get size of actually allocated memory with glibc:

#include <stdlib.h>                                                          
#include <stdio.h>                                                           

int main()                                                                   
{                                                                            
    int n;                                                                   

    for (n = 0; n <= 10; ++n)                                                
    {                                                                        
        void* array = malloc(n * sizeof(int));                               
        size_t* a2 = (size_t*) array;                                        

        printf("%d -> %zu\n", n, a2[-1]);                                    
    }                                                                        
}

对于n< = 6,它分配32个字节,对于7-10,它分配48个字节.

and for n <= 6, it allocates 32 bytes, and for 7-10 it is 48.

因此,如果将int[10]缩小为int[5],则分配的大小将从48缩小到32,从而有效地提供16个空闲字节.由于(如上所述)它不会分配少于32个字节的任何内容,因此这16个字节会丢失.

So, if it shrank int[10] to int[5], the allocated size would shrink from 48 to 32, effectively giving 16 free bytes. Since (as it just has been noted) it won't allocate anything less than 32 bytes, those 16 bytes are lost.

如果将块移动到其他位置,则整个48个字节将被释放,并且实际上可以在其中放置一些内容.当然,那只是一个科幻故事,而不是真正的实现;).

If it moved the block elsewhere, the whole 48 bytes will be freed, and something could actually be put in there. Of course, that's just a science-fiction story and not a real implementation ;).

C99标准中最相关的报价( 7.20.3.4 realloc函数):

The most relevant quote from the C99 standard (7.20.3.4 The realloc function):

返回

4 realloc函数返回指向新对象的指针(可能与指向旧对象的指针具有相同的值),或者如果新对象不能为空,则返回null指针.已分配.

4 The realloc function returns a pointer to the new object (which may have the same value as a pointer to the old object), or a null pointer if the new object could not be allocated.

'May'是此处的关键字.它没有提及何时可能发生的任何特定情况,因此即使乍一看它们似乎很明显,您也不能依靠它们.

'May' is the key-word here. It doesn't mention any specific circumstances when that can happen, so you can't rely on any of them, even if they sound obvious at a first glance.

顺便说一句,我认为您可以考虑将realloc()弃用.如果您看一下C ++,较新的内存分配接口(new/delete和分配器)甚至都不支持这种东西.他们总是希望您分配一个新块.但这只是一个宽松的评论.

By the way, I think you could consider realloc() somewhat deprecated. If you'd take a look at C++, the newer memory allocation interfaces (new / delete and allocators) don't even support such a thing. They always expect you to allocate a new block. But that's just a loose comment.

这篇关于修剪时可以重新分配失败(返回NULL)吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆