树的遍历
1.树的静态写法
用数组下标代替所谓的地址,这需要事先开一个大小不低于结点上限个数的结点数组,因此结构体 node 的定义会类似于下面这样。
struct node{
typename data; //数据域
int child[maxn]; //指针域,存放所有子结点的下标
}Node[maxn]; //结点数组,maxn 为结点上限个数
在上面的定义中,由于无法预知子结点的个数,因此 child 数组的长度只能开到最大,这对一些结点个数比较多的题目来说显然是不可接受的。这时需要用到 STL 中的 vector,于是结构体 node 的定义将会变为如下形式:
struct node{
typename data; //数据域
vector child; //指针域,存放所有子结点的下标
}Node[maxn]; //结点数组,maxn 为结点上限个数
当需要新建一个结点时,按顺序从数组中取出一个下标即可:
int index = 0;
int newNode(int v){
Node[index].data = v; //数据域
Node[index].child.clear(); //清空子结点
return index++; //返回结点下标,并令 index 自增
}
2.树的先根遍历
树的先根遍历个二叉树的先根遍历思想基本一致,先访问根结点,再去访问所有的子结点:
void preOreder(int root){
printf("%d ",Node[root].data); //访问当前结点
for(int i = 0;i < Node[root].child.size();i++){
preOreder(Node[root].child[i]); //递归访问当前结点 root 的所有子结点
}
}
3.树的层次遍历
树的层次遍历实现方法与二叉树类似,一般是使用一个队列来存放结点在数组中的下标,每次取出队首元素来访问,并将其所有的子结点加入队列,直到队列为空。
void layerOrder(int root){
queue<int> q;
q.push(root);
while(!q.empty()){
int front = q.front();
printf("%d ",Node[front].data);
q.pop();
for(int i = 0;i < Node[front].child.size();i++){
q.push(Node[front].child[i]); //将当前结点的所有子结点加入队列
}
}
}