区别是什么:

ptr = malloc(MAXELEMS * sizeof(char *));

And:

ptr = calloc(MAXELEMS, sizeof(char*));

什么时候使用calloc优于malloc或反之亦然?


当前回答

有两个不同之处。 首先,是参数的数量。Malloc()接受一个参数(以字节为单位的内存需求),而calloc()需要两个参数。 其次,malloc()不会初始化分配的内存,而calloc()会将分配的内存初始化为ZERO。

Calloc()分配一个内存区域,长度将是其参数的乘积。calloc用0填充内存,并返回指向第一个字节的指针。如果它不能找到足够的空间,它返回一个NULL指针。

语法:ptr_var = calloc(no_of_blocks, size_of_each_block); 即ptr_var = calloc(n, s);

malloc()分配REQUSTED SIZE的单个内存块,并返回指向第一个字节的指针。如果它无法找到所请求的内存量,它返回一个空指针。

语法:ptr_var = malloc(Size_in_bytes); malloc()函数有一个参数,即分配的字节数,而calloc()函数有两个参数,一个是元素的数量,另一个是为每个元素分配的字节数。另外,calloc()将分配的空间初始化为0,而malloc()不会。

其他回答

有两个不同之处。 首先,是参数的数量。Malloc()接受一个参数(以字节为单位的内存需求),而calloc()需要两个参数。 其次,malloc()不会初始化分配的内存,而calloc()会将分配的内存初始化为ZERO。

Calloc()分配一个内存区域,长度将是其参数的乘积。calloc用0填充内存,并返回指向第一个字节的指针。如果它不能找到足够的空间,它返回一个NULL指针。

语法:ptr_var = calloc(no_of_blocks, size_of_each_block); 即ptr_var = calloc(n, s);

malloc()分配REQUSTED SIZE的单个内存块,并返回指向第一个字节的指针。如果它无法找到所请求的内存量,它返回一个空指针。

语法:ptr_var = malloc(Size_in_bytes); malloc()函数有一个参数,即分配的字节数,而calloc()函数有两个参数,一个是元素的数量,另一个是为每个元素分配的字节数。另外,calloc()将分配的空间初始化为0,而malloc()不会。

calloc的一个经常被忽视的优点是,它将帮助保护您免受整数溢出漏洞的侵害。比较:

size_t count = get_int32(file);
struct foo *bar = malloc(count * sizeof *bar);

vs.

size_t count = get_int32(file);
struct foo *bar = calloc(count, sizeof *bar);

如果count大于SIZE_MAX/sizeof *bar,前者可能导致少量分配和后续缓冲区溢出。在这种情况下,后者将自动失败,因为无法创建如此大的对象。

当然,您可能不得不注意不符合规范的实现,这些实现简单地忽略了溢出的可能性……如果在您的目标平台上存在这个问题,那么无论如何都必须对溢出进行手动测试。

malloc()和calloc()是来自C标准库的函数,它们允许动态内存分配,这意味着它们都允许在运行时分配内存。

他们的原型如下:

void *malloc( size_t n);
void *calloc( size_t n, size_t t)

两者的区别主要有两点:

行为:malloc()分配一个内存块,不初始化它,从这个块中读取内容将导致垃圾值。另一方面,Calloc()分配一个内存块并将其初始化为0,显然读取这个块的内容将导致为0。 语法:malloc()有一个参数(要分配的大小),calloc()有两个参数(要分配的块的数量和每个块的大小)。

如果成功,两者的返回值都是指向已分配内存块的指针。否则返回NULL,表示内存分配失败。

例子:

int *arr;

// allocate memory for 10 integers with garbage values
arr = (int *)malloc(10 * sizeof(int)); 

// allocate memory for 10 integers and sets all of them to 0
arr = (int *)calloc(10, sizeof(int));

使用malloc()和memset()可以实现与calloc()相同的功能:

// allocate memory for 10 integers with garbage values   
arr= (int *)malloc(10 * sizeof(int));
// set all of them to 0
memset(arr, 0, 10 * sizeof(int)); 

注意malloc()最好比calloc()使用,因为它更快。如果需要对值进行零初始化,则使用calloc()。

The documentation makes the calloc look like malloc, which just does zero-initialize the memory; this is not the primary difference! The idea of calloc is to abstract copy-on-write semantics for memory allocation. When you allocate memory with calloc it all maps to same physical page which is initialized to zero. When any of the pages of the allocated memory is written into a physical page is allocated. This is often used to make HUGE hash tables, for example since the parts of hash which are empty aren't backed by any extra memory (pages); they happily point to the single zero-initialized page, which can be even shared between processes.

任何对虚拟地址的写都被映射到一个页,如果该页是零页,则分配另一个物理页,将零页复制到那里,并将控制流返回给客户端进程。这与内存映射文件、虚拟内存等工作方式相同。它使用分页。

下面是一个关于这个主题的优化故事: http://blogs.fau.de/hager/2007/05/08/benchmarking-fun-with-calloc-and-zero-pages/

在<stdlib.h>标头中声明的calloc()函数比malloc()函数提供了几个优点。

它将内存分配为一定数量的给定大小的元素 它初始化所分配的内存,这样所有的位都是 零。