【问题标题】:Why does dereferencing two handles to the same pointer result in this unexpected behavior?为什么取消对同一个指针的两个句柄的引用会导致这种意外行为?
【发布时间】:2021-06-19 17:51:38
【问题描述】:
typedef struct node_t {
    char val;
    node_t * next;
};


void removeNodeByVal(node_t * head, char to_remove) {
    //get head pointer pointer
    node_t** pp = &head;
    node_t** fpp = &head;
    
    // get head pointer
    node_t* entry = head;

    while (entry) {
        if (entry->val == to_remove) {
            *pp = entry->next;
            //*fpp = entry->next <--- this isn't working for me;

            return;
        }
            

        pp = &entry->next;
        entry = entry->next;
        fpp = &entry;
    }
}

在上面的代码sn-p中,代码只有在pp作为指针指针来抓取链表中一个条目的地址,并改变它指向下一个节点时,才会移除目标节点。如果我使用fpp 作为句柄,那么即使fpppp 指向同一个地址,节点的地址也不会改变。有人知道为什么吗?

【问题讨论】:

  • 我的猜测是可能存在未定义的行为,因为在链表的末尾,条目将为 NULL(或 NULLPTR),并且获取 NULL 的地址会导致问题。不过还是让我很烦。
  • 无论是*pp = entry-&gt;next; 还是*fpp = entry-&gt;next;,无论哪种方式,您都只是从您的参数列表中修改head...这是函数的本地参数。如果您尝试在其自己的范围内修改传入的变量,则需要传递 node_t ** 而不是 node_t * 而不是尝试在函数主体内添加额外的间接(这不起作用)。您需要传递要修改的指针的地址......现在您传递它的值,然后获取指向您将其复制到的参数的指针并通过它修改您的参数(而不是原始指针 var)跨度>
  • *pp = entry-&gt;next; 确实有效
  • 它不应该.. 可能还有其他原因导致其他地方出现未定义的行为,可能是在调用这个的函数中。
  • 我想我明白你在说什么。我在搞乱代码,代码 sn-ps 都不能通过间接方式从列表中删除头部。 *pp = entry-&gt;next 仅在能够通过&amp;entry-&gt;next 赋值获得真实指针地址的情况下才有效。我需要学习更多关于在函数中使用指针的知识。

标签: c++ c pointers dereference


【解决方案1】:

如果entry 的值发生变化,&amp;entry-&gt;next 的值也会发生变化。不同的条目将有其next 成员在不同的地址。

但是,由于 entryremoveNodeByVal 函数的局部变量,&amp;entry 将始终具有相同的值。即使entry发生变化,它仍然是同一个内存地址的同一个局部变量。

所以&amp;entry&amp;entry-&gt;next 会有完全不同的行为。一个不会随着entry 的值而改变,并且在整个函数中都是一个常数,另一个会随着循环的每次迭代而改变值。

【讨论】:

    猜你喜欢
    • 2013-04-21
    • 2021-01-03
    • 1970-01-01
    • 2020-11-01
    • 1970-01-01
    • 2017-09-28
    • 2012-07-21
    • 1970-01-01
    • 2010-11-09
    相关资源
    最近更新 更多