【问题标题】:C tutorial question relating to calloc vs malloc与 calloc 与 malloc 相关的 C 教程问题
【发布时间】:2011-01-13 22:33:46
【问题描述】:

我正在关注这个tutorial (http://theocacao.com/document.page/234)。我对这一段感到困惑,主要是与 calloc 相关的几行:

我们还可以使用 malloc 函数的变体,称为 calloc。 calloc 函数有两个参数,一个值计数和基值大小。 它还会在返回指针之前清除内存,这有助于避免不可预知的行为和某些情况下的崩溃:

最后一行让我很困惑。清除内存是什么意思?

【问题讨论】:

    标签: c memory memory-management pointers


    【解决方案1】:

    函数 calloc 将确保返回的内存中的所有字节都设置为 0。 malloc 不做这样的保证。它返回的数据可以并且将由看似随机的数据组成。

    这种区别对于数据成员的初始化非常有用。如果 0 是结构中所有值的良好默认值,那么 calloc 可以简化结构的创建。

    Foo* pFoo = calloc(1, sizeof(Foo));
    

    对比

    Foo* pFoo = malloc(sizeof(Foo));
    pFoo->Value1 = 0;
    pFoo->Value2 = 0;
    

    为清楚起见省略了空值检查。

    【讨论】:

    • ...如果没有正确初始化内存,你会得到不可预知的结果。
    • 如果你也打算使用realloc(),你必须处理额外的内存没有归零的事实——所以你可能需要你的初始化代码来彻底完成这项工作(足够了)。显然,如果你calloc()内存并且永远不会realloc()它,那么这没关系。
    • “将由看似随机的数据组成” - 对于某些“随机”值。统计测试很可能能够将其与 0 ... UCHAR_MAX 范围内均匀分布的离散随机变量的连续样本区分开来;-)
    【解决方案2】:

    准确地说:

    这有助于避免 不可预知的行为和崩溃 某些情况

    应改为:

    这在隐藏时很有用 不可预知的行为和崩溃 某些情况

    【讨论】:

      【解决方案3】:

      在这种情况下,“清除内存”意味着用物理全零位模式填充它。请注意,从形式上看,这种原始内存初始化只保证适用于整数类型。 IE。整数类型的对象保证接收初始值为零。任何其他类型是否会被有意义地初始化是实现定义的。 (需要超出 C 标准限制的附加标准才能提供额外的保证。POSIX、IEEE 754 等)

      如引用中所述使用calloc 来“防止崩溃”实际上是否有意义是另一个问题。我想说它确实可以提高懒惰程序员编写的代码的稳定性,它会将各种垃圾值触发的所有可能的意外行为折叠成一个由全零值触发的特定意外行为。

      【讨论】:

        【解决方案4】:

        malloc() 函数分配内存块但不初始化分配的内存。如果我们尝试访问内存块的内容,那么我们将得到垃圾值。

        calloc() 函数将分配的内存分配并初始化为零。 如果我们尝试访问内存块的内容,那么我们将得到 0。

        不是:如何将malloc() 函数用作calloc()

        通过使用string.h库的memset()函数,malloc()函数可以用作calloc()函数,如下所示。

        int *ptr;
        ptr=malloc(size);
        memset(ptr,0,size);
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2015-12-18
          • 2017-12-24
          • 2013-11-14
          • 2011-09-16
          • 1970-01-01
          • 2021-05-20
          • 1970-01-01
          相关资源
          最近更新 更多