【问题标题】:How to free memory to a pointer in c如何将内存释放到c中的指针
【发布时间】:2016-10-14 18:12:07
【问题描述】:

我有这个(坏的)代码

void function(deq** dq, int data)
{
  // TODO: add a new element at the end of the queue
  deq *temp = (dequeue*)malloc(sizeof(dequeue));
  deq *copy = (*dq);
  temp->data = data;


  if (copy == NULL) {
    temp->next = NULL;
    temp->prev = NULL;
    (*dq) = temp;
  }
  else{
    while (copy->next != NULL) {
      copy = copy->next;
    }

    temp->prev = copy;
    temp->next = NULL;
    copy->next = temp;
    (*dq) = temp;
  }

  //free(temp);
}

我的问题是我无法在不使程序崩溃的情况下释放 temp 有没有办法解决这个问题?有人能告诉我为什么当我免费使用这个程序时,我无法运行该程序,但使用 valgrind 它可以工作......太有趣了。

==17186== HEAP SUMMARY:
==17186==     in use at exit: 216 bytes in 9 blocks
==17186==   total heap usage: 15 allocs, 6 frees, 360 bytes allocated
==17186== 
==17186== 72 (24 direct, 48 indirect) bytes in 1 blocks are definitely lost in loss record 8 of 9
==17186==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==17186==    by 0x400670: dequeue_push_front (dequeue.c:12)
==17186==    by 0x400A1D: main (main.c:21)
==17186== 
==17186== 144 (24 direct, 120 indirect) bytes in 1 blocks are definitely lost in loss record 9 of 9
==17186==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==17186==    by 0x400670: dequeue_push_front (dequeue.c:12)
==17186==    by 0x400BA3: main (main.c:48)
==17186== 
==17186== LEAK SUMMARY:
==17186==    definitely lost: 48 bytes in 2 blocks
==17186==    indirectly lost: 168 bytes in 7 blocks
==17186==      possibly lost: 0 bytes in 0 blocks
==17186==    still reachable: 0 bytes in 0 blocks
==17186==         suppressed: 0 bytes in 0 blocks
==17186== 
==17186== For counts of detected and suppressed errors, rerun with: -v
==17186== ERROR SUMMARY: 2 errors from 2 contexts (suppressed: 0 from 0)

【问题讨论】:

  • 为什么你们都通过*dq输出地址,并在函数结束时释放它?
  • 我知道免费是不好的,但如果我把它注释掉,那么我就会得到那些内存泄漏
  • free 不错不好。这是你应该做的清理自己的事情。它只需要正确完成。

标签: c memory malloc free


【解决方案1】:

你不想在这个函数中free(temp)

此函数使用malloc 在堆上分配temp,然后将节点放入列表中。如果您free() 刚刚在此处分配的内存,则在列表中会留下一个指向无效内存的节点。引用该节点会导致未定义的行为,在本例中表现为核心转储。

调用free() 的适当时间是从列表中删除节点时。

至于内存泄漏,发生在 else 块中。

您将temp 放在列表的末尾,然后用temp 覆盖列表的开头,因此您对列表其余部分的唯一引用是在tempprev 指针中.但是,既然那是您的新负责人,您在清理时可能不会费心看prev。所以你有内存泄漏。

要修复泄漏,请删除对*dq 的分配:

...
else {
    while (copy->next != NULL) {
      copy = copy->next;
    }

    temp->prev = copy;
    temp->next = NULL;
    copy->next = temp;
}
...

【讨论】:

  • 我有一个销毁函数,它循环到节点并删除它们,但仍然会出现内存泄漏,valgrind 告诉我这个
  • '==17186== 1 个块中的 72 个(24 个直接,48 个间接)字节肯定会丢失在丢失记录 8 of 9 ==17186== at 0x4C2AB80: malloc (in /usr/lib /valgrind/vgpreload_memcheck-amd64-linux.so) ==17186== by 0x400670: dequeue_push_front (dequeue.c:12) ==17186== by 0x400A1D: main (main.c:21) ==17186== '
  • hm...当我使用它时,我得到了不好的结果,只有 000 但它应该是数字
  • @twistedhat 这个问题不在发布的代码中。我们需要查看您的完整代码。
  • 所以您认为问题出在其他地方?我不能将完整的代码发布到 big 并且它是拼贴的私人项目。
【解决方案2】:

您正在调用free(temp),但在行中继续使用temp 的值

(*dq) = temp;

copy->next = temp;

不要打电话给free(temp)。确保通过遍历链表并在所有节点上调用free来释放调用函数中的所有内存。

freed 之后访问内存会导致未定义的行为。

顺便说一句,你第二次使用

(*dq) = temp;

导致内存泄漏。删除该行。

【讨论】:

    猜你喜欢
    • 2017-03-01
    • 2016-03-06
    • 1970-01-01
    • 2019-03-14
    • 2017-05-03
    • 1970-01-01
    • 2022-09-27
    • 1970-01-01
    • 2012-12-28
    相关资源
    最近更新 更多