将元组转换为树

时间:2010-10-28 18:23:53

标签: algorithm

我有(Parent1 - > Child1),(Parent2 - > Child2),....,(ParentN - > ChildN)元组描述的有向无环图(树)。是否有任何算法可以从这些信息中重建树(图)?

一个更好的例子:

Root
  Parent1
     Node1
       Child1
       Child2
  Parent2
     Node1
       Child1
       Child2

作为输入我只有:

Root -> Parent1
Node1 -> Child1
Root -> Parent2
Parent1 -> Node1
Parent2 -> Node1
Node1 -> Child2

没有特别的顺序。

只有这些元组,我们可以在以下结构中重建树:

Node(name:String,children:List)?

2 个答案:

答案 0 :(得分:2)

我不清楚你是否在寻找指针数据结构。您正在寻找的是,最终您应该能够列出节点的所有子节点。如果这是要求,您可以做的是创建一个哈希表(根据您的示例,从字符串到字符串)。然后在您的文件中,readline循环将父级设置为哈希表中的键,将字符串向量设置为相应的值。将孩子推到这个载体上。在C ++中,它将如下所示

#include <hash_map>
#include <vector>
#include <string>
using namespace std;
hash_map<string, vector<string>* > graph;
string parent, child;

然后在文件readline循环中

cin >> parent >> child >> child;
if ( graph[parent] == graph.end() ) {
    graph[parent] = new vector<string>();
}
graph[parent]->push_back(child);

请记住在完成后删除矢量,或使用auto_ptr。

在伪代码中:

for every tuple:
    create HashTable entry with key = tuple.parent
    HashTable[tuple.parent].addToList(tuple.child)

答案 1 :(得分:1)

从根开始执行深度优先遍历,允许多次访问节点(当然,图形必须是非循环的才能终止)。对于您访问的每个图节点,您创建一个相应的树节点,并将其连接到其父图节点的相应树节点(编辑:实际上,图节点可以对应多个树节点,你对最后一个感兴趣)。

例如,假设你的根是A

    A
   / \
  /   \
 B     C
  \   /
   \ /
    D

您访问A,创建tA。遍历转到B,您创建tB,将其连接到tA。然后你访问'D',创建tD,将其连接到tB,然后你回溯并访问'C',创建tC并将其连接到tA,这样你得到这棵树:

    tA
   / \
  /   \
 tB   tC
 |    |
 |    |
 tD   tD' 

请注意,与图形相比,通过这种转换可能会获得指数级更大的树。