C for循环中的内存泄漏 for(k=i;kserver_ptr[k+1]!=NULL){ slist->servers_ptr[k]=slist->servers_ptr[k+1]; }else slist->servers\u ptr[k]=NULL; }
当我运行valgrind时,我得到一个无效大小为8的错误 我假设这与for循环中的边界情况有关,但我不明白它是如何发生的 编辑:有人指出,在for循环的最后一轮中,访问服务器\u ptr[k+1]在阵列之外,导致valgrind错误。此后,我将代码更新为:C for循环中的内存泄漏 for(k=i;kserver_ptr[k+1]!=NULL){ slist->servers_ptr[k]=slist->servers_ptr[k+1]; }else slist->servers\u ptr[k]=NULL; },c,memory-leaks,for-loop,valgrind,C,Memory Leaks,For Loop,Valgrind,当我运行valgrind时,我得到一个无效大小为8的错误 我假设这与for循环中的边界情况有关,但我不明白它是如何发生的 编辑:有人指出,在for循环的最后一轮中,访问服务器\u ptr[k+1]在阵列之外,导致valgrind错误。此后,我将代码更新为: for(k=i; k<MAXRECORDS; k++) { if(slist->servers_ptr[k+1] != NULL) { slist->servers_ptr[k] = slist-&g
for(k=i; k<MAXRECORDS; k++) {
if(slist->servers_ptr[k+1] != NULL) {
slist->servers_ptr[k] = slist->servers_ptr[k+1];
} else slist->servers_ptr[k] = NULL;
}
for(k=i;kserver_ptr[k+1]!=NULL){
slist->servers_ptr[k]=slist->servers_ptr[k+1];
如果(k==MAXRECORDS-2)slist->servers\u ptr[k+1]=NULL;
}else slist->servers\u ptr[k]=NULL;
}
我仍然会在valgrind中发现错误。我更新不正确吗?根据的
条件,这看起来像是一个bug:
for(k=i; k<MAXRECORDS-1; k++) {
if(slist->servers_ptr[k+1] != NULL) {
slist->servers_ptr[k] = slist->servers_ptr[k+1];
if(k==MAXRECORDS-2)slist->servers_ptr[k+1] = NULL;
} else slist->servers_ptr[k] = NULL;
}
因为它将读取超过服务器\u ptr
数组的末尾
将条件更改为k
如果slist->servers\u ptr
是一个大小为MAXRECORDS
的数组,那么当k=MAXRECORDS-1
时,访问元素k+1
将超出数组的边界
因为0是数组的第一个元素,所以10是数组的第十一个元素。大小为10的数组没有第十一个元素。这几乎可以肯定,因为您要超出数组的末尾。k
的最大值是MAXRECORDS-1
,您在表达式中使用了k+1
这意味着您将访问array[MAXRECORDS]
,其中索引应限制在0
和MAXRECORDS-1(含)之间
在没有更多上下文的情况下,很难看到您正在尝试做什么,但是修复可能很简单,就像使用k
作为循环继续条件(中间的位):
只有最后一次分配才可访问
顺便说一句,如果你想要的是随机删除,那么(在我看来)最好是这样做:
//对于存在非空下一个元素的每个元素,
//将该元素向下移动。然后强制最后一个元素
//为空(它将已经下移)。
对于(k=i;(kservers_ptr[k+1]!=NULL);k++)
slist->servers_ptr[k]=slist->servers_ptr[k+1];
slist->servers\u ptr[k]=NULL;
额外条件在下一个元素为NULL时停止,并将NULL放置到该位置。这应该可以很好地工作,并且具有不太复杂的优点。MAXRECORDS=10,并且slist->servers\u ptr[]是大小MAXRECORDS。这不是内存泄漏,Valgrind消息告诉您正在覆盖或过度读取分配内存的边界(在您的案例数组中)。您是否将servers\u ptr
声明为servers\u ptr[MAXRECORDS+1]
?否则,当k=MAXRECORDS-1
时,您的阅读就到此为止了。将额外信息添加到问题中,而不是作为注释。我这次为您做了这件事,但为了将来。(您可以删除我为您传输的注释;但我不能这样做。)谢谢你们的回复,伙计们。它声明为servers_ptr[MAXRECORDS]。我更新了我的问题,我的解决方案在逻辑上解决了吗?这很有意义。谢谢!我更新了for循环中的边界,但仍然在valgrind中遇到同样的问题。谢谢:)我更改了for循环中的条件,但仍然出现错误:(那更干净了,你说得对。解释得也很好,我来试试看。
if((slist->servers_ptr[k+1] != NULL)
for (k = i; k < MAXRECORDS - 1; k++) {
char *x;
for (i = 0; i < 10; i++)
x = malloc (64);
// For every element where there's a non-NULL next element,
// shift that element down. Then force the last element to
// be NULL (it will have been shifted down already).
for (k = i; (k < MAXRECORDS - 1) && (slist->servers_ptr[k+1] != NULL); k++)
slist->servers_ptr[k] = slist->servers_ptr[k+1];
slist->servers_ptr[k] = NULL;