我知道如何对二进制搜索树进行编码,以及如何以有序,前置或后置方式遍历它。 但是,我想知道如何知道实际节点在哪里:
例如,我们有以下值:70 90 50 60 80 40 因此根将是70、90右边,50左边,60到50等,以此类推。
因此,如果我要打印此订单,它将是40 50 60 70 80 90,这将大大增加订单数。 我是通过在递归遍历函数中执行此操作的:
traverse(root->left);
printf("%d ", root->data);
traverse(root->right);
但是,这并不能让我知道(据我所知)该节点当前在哪里。 有没有办法像这样打印树?:
70
50(70 L)90(70 R)//我们知道节点来自哪个父节点,也知道它是节点的左边还是右边。
40(50升)60(50 R)80(90升)
,依此类推..如果树更大。 我真的不知道该怎么做。我需要将它们链接到他们的父母吗?但是,如果我那样做,我怎么会知道左右事物呢?还是在迭代器仍位于父项上时需要打印子项。预先谢谢你。
编辑:我查找了逐级遍历打印树的方法,但是我想我不了解父级和节点侧。我试图将一些代码实现为c代码,但我总是得到崩溃。
答案 0 :(得分:1)
似乎您要逐级打印树,即
level 0: node0
level 1: node1 (node0 L) node2 (node0 R)
level 2: ...
因此,您需要一种跟踪当前级别和目标级别(即您要打印的级别)的方法。另外,您还需要一种方法来跟踪何时“没有更多的级别”(即不再需要打印)。
这可以通过多种方式完成。下面的伪代码应为您提供一种实现方法的思路。这不是最有效的方法,但是非常简单。
类似的东西:
bool btPrintLevel(node* root, int targetlevel, int currentlevel)
{
if (targetlevel == currentlevel) return false; // no need to go further down in levels
bool result = false;
result |= btPrintLevel(root->left, targetlevel, currentlevel + 1);
// psedo code
if ((currentlevel + 1 == targetlevel)
{
if (childern_exists)
{
printChildern(...)
result = true;
}
}
result |= btPrintLevel(root->right, targetlevel, currentlevel + 1);
return result;
}
称呼为:
int level = 0;
while(btPrintLevel(head, level)) ++level;
此How to print elements from Binary Tree by level in c可能也有帮助。它并不能完全满足您的要求,但只需稍加修改即可实现您的目标。
答案 1 :(得分:0)
递归算法适合于树的深度优先遍历,但不适用于宽度优先。使用FIFO(伪代码)可以非常有效地完成后者:
push(fifo, { root, 0 });
while(!isEmpty(fifo))
{
node* n = pop(fifo);
print(n);
if(n->left)
push(fifo, { n->left, 'L' });
if(n->right)
push(fifo, { n->right, 'R'});
}
我已经预见到一个额外的字段,它指定是父母的左子女还是右子女。如果您的节点具有到其父节点的链接,则可以改为决定n->parent->left == n ? 'L' : 'R'
。
让您自己实施FIFO(关于SO的问题很多)...