与C中的calloc相反的是什么

时间:2014-03-25 22:37:08

标签: c calloc

这不仅仅是一个有趣的问题。 : - )

我希望在C中初始化一个数组,而不是用calloc将数组清零。我想将所有元素设置为一个。有没有一个功能可以做到这一点?

我上面用我的问题搜索谷歌,没有答案。希望你能帮助我!仅供参考,我是第一年开始在C学习的CS学生。

3 个答案:

答案 0 :(得分:6)

没有标准的C内存分配功能,允许您指定分配的内存初始化为0以外的值。

您可以轻松编写封面功能来完成工作:

void *set_alloc(size_t nbytes, char value)
{
    void *space = malloc(nbytes);
    if (space != 0)
        memset(space, value, nbytes);
    return space;
}

请注意,这假设您要将每个字节设置为相同的值。如果您有更复杂的初始化要求,则需要更复杂的功能。例如:

void *set_alloc2(size_t nelems, size_t elemsize, void *initializer)
{
    void *space = malloc(nelems * elemsize);
    if (space != 0)
    {
        for (size_t i = 0; i < nelems; i++)
            memmove((char *)space + i * elemsize, initializer, elemsize);
    }
    return space;
}

使用示例:

struct Anonymous
{
    double d;
    int    i;
    short  s;
    char   t[2];
};

struct Anonymous a = { 3.14159, 23, -19, "A" };

struct Anonymous *b = set_alloc2(20, sizeof(struct Anonymous), &a);

答案 1 :(得分:3)

memset适合您:

memset(array, value, length);

答案 2 :(得分:1)

没有这样的功能。您可以使用malloc()memset()(用于字符数据)或for循环(用于其他整数数据)自行实现。

calloc()函数存在的推动力(与malloc() + memset()相比)是在某些情况下它可以是一个不错的性能优化。如果您要分配大量数据,操作系统可能会为您提供一系列已初始化为零的虚拟地址,从而节省了手动将0写入该内存范围的额外成本。这可能是一个很大的性能提升,因为在实际使用它们之前,您不需要将所有这些页面都分页。

在幕后,calloc()可能看起来像这样:

void *calloc(size_t count, size_t size)
{
    // Error checking omitted for expository purposes
    size_t total_size = count * size;
    if (total_size < SOME_THRESHOLD)  // e.g. the OS's page size (typically 4 KB)
    {
        // For small allocations, allocate from normal malloc pool
        void *mem = malloc(total_size);
        memset(mem, 0, total_size);
        return mem;
    }
    else
    {
        // For large allocations, allocate directory from the OS, already zeroed (!)
        return mmap(NULL, total_size, PROT_READ|PROT_WRITE, MAP_ANON|MAP_PRIVATE, -1, 0);
        // Or on Windows, use VirtualAlloc()
    }
}