测试树形圆度?

时间:2011-11-22 07:10:14

标签: c tree

我对数据结构仍然不是很了解,但我有这个家庭作业要求我测试一个树状结构是否是圆形的。也就是说,以某种形式,节点的左右指针最终指向较早的节点。

我一直试图想出几个小时的递归函数,但我似乎无法得到它。我也没有太多的工作要展示它。 有人可以给我一些关于如何做到这一点的想法吗? 我们使用的语言是C。

感谢。

3 个答案:

答案 0 :(得分:2)

通常,最好的方法是使用深度优先搜索(DFS)。从根节点开始,将其标记为“已访问”,然后开始按照指针进行操作。在您到达的每个新节点上,将其标记为“已访问”。如果你达到了死胡同,请备份并尝试另一条路径。

如果您按照指针并到达已标记为已访问过的节点,那么您就有了一个循环。

如何递归地执行:

struct node {
    struct node *left;
    struct node *right;
    bool visited;
};

bool check_tree(struct node *cur)
{
    if (cur == NULL)
        return true;

    if (cur->visited)
        return false; // uh oh. We've been here...
    cur->visited = true;
    return check_tree(cur->left)
           && check_tree(cur->right);
 }

 if (check_tree(&root))
     printf("No self-references here.\n");

(警告:代码可能有错误)

答案 1 :(得分:1)

您需要查看Topological Sort算法。

您将注意到维基百科链接上提供的伪代码,在排序过程中,您将了解任何循环引用。

L ← Empty list that will contain the sorted elements
S ← Set of all nodes with no incoming edges
while S is non-empty do
    remove a node n from S
    insert n into L
    for each node m with an edge e from n to m do
        remove edge e from the graph
        if m has no other incoming edges then
            insert m into S
if graph has edges then
    **output error message (graph has at least one cycle)**
else 
    output message (proposed topologically sorted order: L)

编辑:

这个答案是在作者表示他基本上有一个双链表结构之前发布的。我发布它不是因为我认为它在所有情况下都是最有效的答案,但是由于我们缺乏关于他的图表的信息(除了它作为“树”的描述),这个答案应该处理大多数情况。

答案 2 :(得分:1)

Floyd的'Tortoise& Hare'算法应该非常优雅地解决这个问题。请看这里:http://en.wikipedia.org/wiki/Cycle_detection

它非常适合列表,但也可以适用于像树一样走树。