8

可能重复:
c malloc 和 calloc 的区别
为什么 calloc 需要两个参数而 malloc 只需要一个参数?

我注意到许多 C 函数调用特别是那些处理内存或文件操作的函数,但并非所有函数都使用这两个参数。例如 malloc 传递了一个参数,即所需内存空间的大小(以字节为单位)。另一方面,Calloc 被传递了两个参数,一个元素的字节大小和元素的数量(大小和 nmem)。还有其他函数也使用这些大小和 nmem 参数。

本质上,calloc 调用将分配与调用 malloc(nmem size) 相同的内存量,所以真正发生的只是星号 ( ) 被替换为逗号 (,)。至少这是我能从我工作的更高层次上知道的全部内容。我看不出调用 calloc(1, nmem size)、calloc(nmem size, 1) 或 calloc(nmem, size) 有什么不同。

是否在较低级别上实际发生了某些事情,使得调用例如 calloc(1, nmem*size) 与 calloc(nmem, size) 根本不同?

编辑:我知道 calloc 和 malloc 之间的功能区别。我对为什么参数存在差异感兴趣。还有其他函数使用 2 个大小参数作为总大小(fread、fwrite 等)。我不关心具体的函数,而是为什么函数中使用的总大小有两个参数,而实际上总大小变成了两个参数相乘。我发现大多数时候,当我使用这些函数时,我在“size”参数中使用我需要的大小,在“nmem”(有时是“count”等)参数中使用“1”。

4

2 回答 2

2

在对该问题的评论中,我写道,它calloc()可以为重要的平台提供更好的内存对齐。我还没有找到任何支持(还)的东西。我很确定这是 VMS/VAXC 编译器的一个特性,但它的源代码很少。


然而,我确实发现了这一点,calloc()并且alloc()与 1975 年 5 月发布的 Unix V6 同时出现。在 11 个月前发布的 V5 中,这两个功能都不存在。内核和运行时库(以及汇编器和 C 编译器)是用汇编语言编写的。

在 V6 版本中,calloc 被实现为四行源代码模块:

calloc(n, s)
{
return(alloc(n*s));
}

calloc()不清除分配的内存;看,在 V6alloc()中没有man页面;calloc()但是手册页alloc()

说明
Allocfree提供了一个简单的通用核心管理包。 Alloc的大小以字节为单位;它返回一个指向一个区域的指针,该区域的大小至少是偶数,因此可以容纳任何类型的对象。free的参数 是指向先前由alloc 分配的区域的指针;该空间可供进一步分配。

不用说,如果alloc分配的空间被溢出或者某个随机数被交给free,就会导致严重的混乱。

该例程使用首次拟合算法将正在释放的块与其他已经空闲的块合并。 当没有合适的可用空间时,它调用sbrk(参见“break (II))”从系统中获取更多内核。

DIAGNOSTICS如果没有可用内核,则
返回-1 。

BUGS
分配的内存包含垃圾而不是被清除。

NULL在内存耗尽的情况下甚至不返回!

calloc()1979 年 1 月首次正式出现在 UNIX V7 中,同时还有其他一些改进

  • calloc()清除返回的内存。
  • alloc()改名为malloc()
  • realloc()出现了
  • 在内存耗尽或堆错误的情况下,函数“返回空指针 (0)”
于 2012-10-12T18:15:51.810 回答
0

在较低级别上是否确实发生了某些事情,使得调用例如 calloc(1, nmem*size) 与 calloc(nmem, size) 根本不同?

这种解释事物的尝试完全依赖于 libc 的实现——因此需要特定 libc 作者的赞赏:

由于calloc()正在归零内存,其基本原理可能是它可能(可能)在执行mult.

相比之下,malloc()有机会使用预先计算的值,从而可能减少调用中可能更容易满足的开销。

不要忘记,C 是在每个 CPU 周期都耗费大量成本的时候设计的——因此与许多其他“高级”语言相比,它的设计非常精益。

C Dennis Ritchie 的作者可能会更好地回答这个问题。

于 2012-10-12T16:28:41.630 回答