对你们中的一些人来说,这似乎是一个愚蠢的问题,我知道我经常把事情搞混,但我需要理解代码,这样我才能停止沉迷于它,而专注于我为什么需要使用它的真正问题。
所以,在代码中我看到了几个这样的任务:
struct bst_node** node = root;
node = &(*node)->left;
node = &(*node)->right;
is there an invisible parenthesis here?
node = &((*node)->right);
此示例取自 literateprograms.org。
所以对我来说似乎 &(*node) 是不必要的,我不妨只写 node->left ,但代码似乎在我无法理解的地方工作,我想知道是不是因为我我误解了这些线路上发生的事情。特别是,在代码中的一个地方,它通过不断地将“已删除”数据移动到树的底部以安全地删除节点而不必“破坏”来删除节点,我迷路了,因为我没有怎么弄
old_node = *node;
if ((*node)->left == NULL) {
*node = (*node)->right;
free_node(old_node);
else if ((*node)->right == NULL) {
*node = (*node)->left;
free_node(old_node);
} else {
struct bst_node **pred = &(*node)->left;
while ((*pred)->right != NULL) {
pred = &(*pred)->right;
}
psudo-code: swap values of *pred and *node when the
bottom-right of the left tree of old_node has been found.
recursive call with pred;
}
可以保持树结构完整。我不明白这如何确保结构完好无损,并希望知道发生了什么的人提供一些帮助。我将 node 解释为堆栈上的局部变量,在函数调用时创建。由于它是一个双指针,它指向堆栈中的一个位置(我假设这一点,因为他们在函数调用之前做了 &(*node) ),要么是它自己的堆栈,要么是之前的函数,然后指向所述节点在堆上。
在上面的示例代码中,我认为应该做的是向左或向右切换,因为其中一个是 NULL,然后切换不是的(假设另一个不是 NULL?)正如我所说,我不确定这将如何工作。我的问题主要与我认为 &(*node) <=> node 但我想知道是否不是这种情况等有关。