Algorithm UVA#10410树重建
我已经工作了好几天了。但是我现在不能得到正确的答案 我使用了一种类似于我们通常使用的通过前序遍历和顺序遍历来恢复二叉树的算法。但它不能工作Algorithm UVA#10410树重建,algorithm,tree,Algorithm,Tree,我已经工作了好几天了。但是我现在不能得到正确的答案 我使用了一种类似于我们通常使用的通过前序遍历和顺序遍历来恢复二叉树的算法。但它不能工作 有人能帮我吗?提前谢谢。我想我已经掌握了窍门。不过,我并不假装它很有效 让我们看看BFS输出的前3位数字: 4 3 5 我们正处于以下情况之一: 4 4 / \ OR | 3 5 3 x x | 5 x 这两个案例的DFS是多少 4 3(3个孩
有人能帮我吗?提前谢谢。我想我已经掌握了窍门。不过,我并不假装它很有效 让我们看看BFS输出的前3位数字:
4 3 5
我们正处于以下情况之一:
4 4
/ \ OR |
3 5 3
x x |
5
x
这两个案例的DFS是多少
- 4 3(3个孩子)5(5个孩子)
- 4 3 5(5个儿童)
3
没有孩子,那么就无法区分这两个孩子
如果我们认为问题是可判定的,那么在DFS表示中是否知道<代码> 5 遵循<代码> 3 <代码>。
- 如果是:它是一个线性组合
- 如果没有,则返回递归:
有两个子项4
和3
,您可以很容易地从DFS表示中识别子树。然后从您拥有的BFS中提取(保留顺序)这些子树的BFS表示并递归:)5
#包括
#包括
#包括
#包括
使用名称空间std;
结构体类型
{
int值;
Node*child;//左子节点
节点*同级;//右同级
节点(INTV)
{
值=v;
child=NULL;
同级=空;
}
};
void构建树(节点*&根、向量bfs、向量dfs)
{
root=NULL;
如果(bfs.size()==1)
根=新节点(bfs[0]);
如果(bfs.size()>1)
{
根=新节点(bfs[0]);
向量候选;//存储候选子对象
未签名的i;
对于(i=1;i=bfs[1])
候选者。推回(bfs[i]);
其他的
打破
}
//删除非候选节点
int boundOfChild=candidate.size()-1;
对于(i=candidate.size()-1;i>=1;i--)
{
向量::迭代器it1;
向量::迭代器it2;
it1=find(dfs.begin()、dfs.end()、候选者[i]);
it2=find(dfs.begin(),dfs.end(),候选者[i-1]);
如果(it1=1;i--)
{
向量::迭代器it1;
向量::迭代器it2;
如果(i==candidate.size())
{
it1=find(dfs.begin(),dfs.end(),候选者[i-1]);
it2=dfs.end();
}
其他的
{
it1=find(dfs.begin(),dfs.end(),候选者[i-1]);
it2=find(dfs.begin()、dfs.end()、候选者[i]);
}
向量tmp_dfs(it1,it2);
向量tmp_-bfs;
对于(vector::iterator it=bfs.begin();it子节点;
构建树(根->子级、tmp_bfs、tmp_dfs);
根->子->同级=tmp;
}
}
}
无效打印树(节点*根)
{
if(root==NULL)
返回;
队列Q;
推(根);
而(!Q.empty())
{
节点*tmp=Q.front();
Q.pop();
不能重视儿童;
while(tmp)
{
不能重视兄弟姐妹;
}
cout看起来很有趣!这将是我的新玩具问题:我有一个想法。请注意这句话:“注意,当父对象被展开时,子对象被按升序遍历。”。我会尽快粘贴我的代码。我认为可判定性无关紧要。解决方案应该是找到任何适合的树,可以有多个答案。此外,问题陈述中提到的解析树只是故事的一部分,给定的遍历不一定是解析树的遍历:)。它可以是任何树…我知道aven没有提交它,因为函数PrintTree应该重写以满足要求-“按升序”.但我认为我的算法应该是正确的。这似乎很简单。将值输出到一个临时向量,用std::sort
对该向量排序,然后打印该向量。这不是最有效的,但您可以担心以后可能出现的TLE。
#include <iostream>
#include <vector>
#include <queue>
#include <algorithm>
using namespace std;
struct Node
{
int value;
Node *child; //left child
Node *sibling; //right sibling
Node(int v)
{
value = v;
child = NULL;
sibling = NULL;
}
};
void BuildTree(Node *&root,vector<int> bfs,vector<int> dfs)
{
root = NULL;
if(bfs.size() == 1)
root = new Node(bfs[0]);
if(bfs.size() > 1)
{
root = new Node(bfs[0]);
vector<int> candidate; //store candidate childs
unsigned i;
for(i = 1; i < bfs.size(); i++)
{
if(bfs[i] >= bfs[1])
candidate.push_back(bfs[i]);
else
break;
}
//remove the non-candidate node
int boundOfChild = candidate.size() - 1;
for(i = candidate.size() - 1; i >= 1; i--)
{
vector<int>::iterator it1;
vector<int>::iterator it2;
it1 = find(dfs.begin(),dfs.end(),candidate[i]);
it2 = find(dfs.begin(),dfs.end(),candidate[i - 1]);
if(it1 < it2)
boundOfChild = i;
}
if(boundOfChild != candidate.size() - 1)
candidate.erase(candidate.begin() + boundOfChild,candidate.end());
//get every child's bfs and dfs
for(i = candidate.size(); i >= 1; i--)
{
vector<int>::iterator it1;
vector<int>::iterator it2;
if(i == candidate.size())
{
it1 = find(dfs.begin(),dfs.end(),candidate[i - 1]);
it2 = dfs.end();
}
else
{
it1 = find(dfs.begin(),dfs.end(),candidate[i - 1]);
it2 = find(dfs.begin(),dfs.end(),candidate[i]);
}
vector<int> tmp_dfs(it1,it2);
vector<int> tmp_bfs;
for(vector<int>::iterator it = bfs.begin(); it < bfs.end(); it++)
{
if(find(tmp_dfs.begin(),tmp_dfs.end(),*it) != tmp_dfs.end())
tmp_bfs.push_back(*it);
}
Node *tmp = root->child;
BuildTree(root->child,tmp_bfs,tmp_dfs);
root->child->sibling = tmp;
}
}
}
void PrintTree(Node *root)
{
if(root == NULL)
return;
queue<Node*> Q;
Q.push(root);
while(!Q.empty())
{
Node *tmp = Q.front();
Q.pop();
cout << tmp->value << ": ";
tmp = tmp->child;
while(tmp)
{
cout << tmp->value << ",";
Q.push(tmp);
tmp = tmp->sibling;
}
cout << endl;
}
}
//just test case
int BFS[] = {7,8,12,4,5,1,6,11,2,3,10,9,13,14};
int DFS[] = {7,8,4,5,2,3,12,1,6,10,14,11,9,13};
int main()
{
vector<int> vBFS(BFS,BFS + sizeof(BFS) / sizeof(int));
vector<int> vDFS(DFS,DFS + sizeof(DFS) / sizeof(int));
Node *root = NULL;
BuildTree(root,vBFS,vDFS);
PrintTree(root);
return 0;
}