C 无内存混乱

C 无内存混乱,c,memory,free,C,Memory,Free,我有一个关于我的代码的简短问题。我为测试创建了两个场景或示例 例1: char *arr[1000000]; int i = 0; for (; i < 1000000; i++){ char *c = (char *) calloc(1, sizeof(char) * 10); free(c); } char*arr[1000000]; int i=0; 对于(;i

我有一个关于我的代码的简短问题。我为测试创建了两个场景或示例

例1:

char *arr[1000000];
int i = 0;
for (; i < 1000000; i++){
    char *c = (char *) calloc(1, sizeof(char) * 10);
    free(c);
}
char*arr[1000000];
int i=0;
对于(;i<1000000;i++){
char*c=(char*)calloc(1,sizeof(char)*10);
免费(c);
}
例2:

char *arr[1000000];
int i = 0;
for (; i < 1000000; i++){
    char *c = (char *) calloc(1, sizeof(char) * 10);
    arr[i] = c;
    free(arr[i]);
    arr[i] = NULL;
}
char*arr[1000000];
int i=0;
对于(;i<1000000;i++){
char*c=(char*)calloc(1,sizeof(char)*10);
arr[i]=c;
免费(arr[i]);
arr[i]=NULL;
}
示例中的不同之处:在释放内存之前放入数组

当我运行示例1时,它释放了所有内存。当我运行示例2时,它不会释放所有内存。 我找了又找,但找不出来

为什么示例2的结果与示例1不同


我的常识告诉我,示例1和示例2的结果应该是相同的,但实际上并非如此。我使用linux top来检查内存使用情况。

结果是一样的。我不知道你为什么认为两者有区别。

两者都是一样的

由于您使用
top
读取内存,因此可以通过编译器优化来解释这种差异。例如,可以完全优化示例1中的阵列


要检查内存问题,应使用valgrind或类似工具。

这是由请求分页引起的。该进程具有数组的地址空间(即:存在该数组的pagetable条目),但没有附加内存(尚未)。循环将(最终)分配给属于数组[]的所有内存页,因此在循环结束时,所有页都已“出错”

作为概念证明,您可以将循环替换为:

for (; i < 1000000; i++){
    arr[i] = "hello, world!";
}
(;i<1000000;i++)的
{
arr[i]=“你好,世界!”;
}

结果可能(几乎)与代码片段#2中的结果相同。您如何知道它没有释放所有内存?您如何推断第二个示例没有释放所有内存?您检查了什么?进程的RSS?如果你真的认为有剩余的东西,我会在valgrind下运行这两个。@Tim你如何检查内存使用情况?这可能是因为编译器在第一个示例中完全省略了
arr
,因为它没有被使用。顺便说一句,在正常情况下,你不会看到top会减少内存使用。@Mat:当我运行循环的次数越多,内存中的差异就越大frequentely@jpalecek:如果是这样的话,我怎样才能减少内存使用?@TimMeijer:我恐怕说我不太相信,或者你看错了专栏,或者测量其他东西。即使
calloc
不只是在每次迭代中分发相同的块,这最多是流程中10MB的动态分配。没有理由认为进程应该或将在终止之前将其释放回操作系统。