问题(假定根节点位于第0层)
1. 层次遍历二叉树(每层换行分开)
2. 层次遍历二叉树指定的某层
例如
上图中
1.
1 2 3 4 5 6 7 8
2.
第三层 7 8
可以看出得出第二问的解,第一问迎刃而解了,所以从问题二下手
分析与解
1. 层次遍历二叉树指定的某层
可以得出这样的一个结论:遍历二叉树的第k层,相当于遍历二叉树根节点的左右子树的第k-1层。这样一直遍历下去,直到k=0时,输出节点即可。
参考代码
int PrintNodeAtLevel(BiTree root, int level) { if(!root || level < 0) return 0; else if(level == 0) { cout << root->data << endl; return 1; } else return PrintNodeAtLevel(root->left, level - 1) + PrintNodeAtLevel(root->right, level - 1); }
完整执行代码
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<iostream> using namespace std; typedef struct BiTNode { int data; BiTNode *left; BiTNode *right; }BiTNode, *BiTree; void createTree(BiTree &root) { BiTree left1 = new(BiTNode); BiTree right1 = new(BiTNode); left1->data = 1; left1->left = NULL; left1->right = NULL; right1->data = 2; right1->left = NULL; right1->right = NULL; root->left = left1; root->right = right1; BiTree left2 = new(BiTNode); left2->data = 3; left2->left = NULL; left2->right = NULL; BiTree right2 = new(BiTNode); right2->data = 4; right2->left = NULL; right2->right = NULL; left1->left = left2; left1->right = right2; BiTree left3 = new(BiTNode); left3->data = 5; left3->left = NULL; left3->right = NULL; BiTree right3 = new(BiTNode); right3->data = 6; right3->left = NULL; right3->right = NULL; left2->left = left3; left2->right = right3; } void deleteTree(BiTree root) { if(root) { deleteTree(root->left); deleteTree(root->right); delete(root); root = NULL; } } int PrintNodeAtLevel(BiTree root, int level) { if(!root || level < 0) return 0; else if(level == 0) { cout << root->data << endl; return 1; } else return PrintNodeAtLevel(root->left, level - 1) + PrintNodeAtLevel(root->right, level - 1); } int main() { BiTree root = new(BiTNode); root->data = 0; root->right = root->left = NULL; createTree(root); cout << "Level 0:" << endl; PrintNodeAtLevel(root, 0); cout << "-------------------" << endl; cout << "Level 1:" << endl; PrintNodeAtLevel(root, 1); cout << "-------------------" << endl; cout << "Level 2:" << endl; PrintNodeAtLevel(root, 2); cout << "-------------------" << endl; cout << "Level 3:" << endl; PrintNodeAtLevel(root, 3); cout << "-------------------" << endl; deleteTree(root); }
执行结果
2. 层次遍历二叉树
解法1——根据求得的层次,遍历每一层
参考代码
void TranverseTree(BiTree root) { for(int i = 0; i < Height(root); ++i) { PrintNodeAtLevel(root, i); cout << "_____________________________" << endl; } }
完整执行程序
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<iostream> using namespace std; typedef struct BiTNode { int data; BiTNode *left; BiTNode *right; }BiTNode, *BiTree; int maxDis = 0; void createTree(BiTree &root) { BiTree left1 = new(BiTNode); BiTree right1 = new(BiTNode); left1->data = 1; left1->left = NULL; left1->right = NULL; right1->data = 2; right1->left = NULL; right1->right = NULL; root->left = left1; root->right = right1; BiTree left2 = new(BiTNode); left2->data = 3; left2->left = NULL; left2->right = NULL; BiTree right2 = new(BiTNode); right2->data = 4; right2->left = NULL; right2->right = NULL; left1->left = left2; left1->right = right2; BiTree left3 = new(BiTNode); left3->data = 5; left3->left = NULL; left3->right = NULL; BiTree right3 = new(BiTNode); right3->data = 6; right3->left = NULL; right3->right = NULL; left2->left = left3; left2->right = right3; } void deleteTree(BiTree root) { if(root) { deleteTree(root->left); deleteTree(root->right); delete(root); root = NULL; } } int PrintNodeAtLevel(BiTree root, int level) { if(!root || level < 0) return 0; else if(level == 0) { cout << root->data << endl; return 1; } else return PrintNodeAtLevel(root->left, level - 1) + PrintNodeAtLevel(root->right, level - 1); } int Height(BiTree root) { if(root == NULL) return 0; else return Height(root->left) > Height(root->right) ? Height(root->left)+1 : Height(root->right) + 1; } void TranverseTree(BiTree root) { for(int i = 0; i < Height(root); ++i) { PrintNodeAtLevel(root, i); cout << "_____________________________" << endl; } } int main() { BiTree root = new(BiTNode); root->data = 0; root->right = root->left = NULL; createTree(root); TranverseTree(root); deleteTree(root); }
执行结果
解法2——无需求得层次,根据遍历每层的返回信息确定遍历
参考代码
void TranverseTree(BiTree root) { for(int i = 0; ; ++i) { if(!PrintNodeAtLevel(root, i)) break; cout << "_____________________________" << endl; } }
完整执行代码
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<iostream> using namespace std; typedef struct BiTNode { int data; BiTNode *left; BiTNode *right; }BiTNode, *BiTree; int maxDis = 0; void createTree(BiTree &root) { BiTree left1 = new(BiTNode); BiTree right1 = new(BiTNode); left1->data = 1; left1->left = NULL; left1->right = NULL; right1->data = 2; right1->left = NULL; right1->right = NULL; root->left = left1; root->right = right1; BiTree left2 = new(BiTNode); left2->data = 3; left2->left = NULL; left2->right = NULL; BiTree right2 = new(BiTNode); right2->data = 4; right2->left = NULL; right2->right = NULL; left1->left = left2; left1->right = right2; BiTree left3 = new(BiTNode); left3->data = 5; left3->left = NULL; left3->right = NULL; BiTree right3 = new(BiTNode); right3->data = 6; right3->left = NULL; right3->right = NULL; left2->left = left3; left2->right = right3; } void deleteTree(BiTree root) { if(root) { deleteTree(root->left); deleteTree(root->right); delete(root); root = NULL; } } int PrintNodeAtLevel(BiTree root, int level) { if(!root || level < 0) return 0; else if(level == 0) { cout << root->data << endl; return 1; } else return PrintNodeAtLevel(root->left, level - 1) + PrintNodeAtLevel(root->right, level - 1); } void TranverseTree(BiTree root) { for(int i = 0; ; ++i) { if(!PrintNodeAtLevel(root, i)) break; cout << "_____________________________" << endl; } } int main() { BiTree root = new(BiTNode); root->data = 0; root->right = root->left = NULL; createTree(root); TranverseTree(root); deleteTree(root); }
执行结果
解法3——无需求每次都从根说起,一次遍历成功
可以看出,解法1、2每次都需要从根说起,还可以不从跟谈起,一次遍历所有的节点,不过这需要额外的存储空间
思路
定义两个指针:cur、last.cur指向目前该访问的节点位置,last指向目前队列中最后一个元素的后一个位置
遍历每一层时,遍历每一个元素是cur往后移动,同时把cur指向的左右孩子加入到队列中,当cur==last时说明该层已经遍历完事了。
参考代码
void TranverseTree(BiTree root) { vector<BiTree> vec; vec.push_back(root); int cur =0, last = 1; while(cur < vec.size()) { last = vec.size(); while(cur < last) { cout << vec[cur]->data << " "; if(vec[cur]->left) vec.push_back(vec[cur]->left); if(vec[cur]->right) vec.push_back(vec[cur]->right); ++cur; } cout << endl; } }
完整执行代码
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <iostream> #include <vector> using namespace std; typedef struct BiTNode { int data; BiTNode *left; BiTNode *right; }BiTNode, *BiTree; int maxDis = 0; void createTree(BiTree &root) { BiTree left1 = new(BiTNode); BiTree right1 = new(BiTNode); left1->data = 1; left1->left = NULL; left1->right = NULL; right1->data = 2; right1->left = NULL; right1->right = NULL; root->left = left1; root->right = right1; BiTree left2 = new(BiTNode); left2->data = 3; left2->left = NULL; left2->right = NULL; BiTree right2 = new(BiTNode); right2->data = 4; right2->left = NULL; right2->right = NULL; left1->left = left2; left1->right = right2; BiTree left3 = new(BiTNode); left3->data = 5; left3->left = NULL; left3->right = NULL; BiTree right3 = new(BiTNode); right3->data = 6; right3->left = NULL; right3->right = NULL; left2->left = left3; left2->right = right3; } void deleteTree(BiTree root) { if(root) { deleteTree(root->left); deleteTree(root->right); delete(root); root = NULL; } } void TranverseTree(BiTree root) { vector<BiTree> vec; vec.push_back(root); int cur =0, last = 1; while(cur < vec.size()) { last = vec.size(); while(cur < last) { cout << vec[cur]->data << " "; if(vec[cur]->left) vec.push_back(vec[cur]->left); if(vec[cur]->right) vec.push_back(vec[cur]->right); ++cur; } cout << endl; } } int main() { BiTree root = new(BiTNode); root->data = 0; root->right = root->left = NULL; createTree(root); TranverseTree(root); deleteTree(root); }
执行结果
C语言写的
void LevelTraverse(BinaryTreeNode *root) { if(root == NULL) return; BinaryTreeNode* a[MAXSIZE]; a[0] = root; int beg = 0; //表示该层的第一个元素 int end = 0; //表示该层的最后一个元素 int pos_end = 0; //表示目前访问的元素存放的位置 while(beg <= end) { if(a[beg]->m_pLeft != NULL) a[++pos_end] = a[beg]->m_pLeft; if(a[beg]->m_pRight != NULL) a[++pos_end] = a[beg]->m_pRight; cout << a[beg]->m_nValue << " "; ++beg; if(beg > end) { end = pos_end; cout << endl; } } }
之字形打印
例子:例子中打印
1 2 3 6 5 4 7
参考
#include <iostream> #include <vector> using namespace std; struct TreeNode { int val; TreeNode *left; TreeNode *right; TreeNode(int v) : val(v), left(NULL), right(NULL){}; }; void LevelTranverse(TreeNode *root) { if (root == NULL) return; vector<TreeNode *> vec; vec.push_back(root); int beg = 0; int end = vec.size(); bool L2R = false; while (beg != end) { if (L2R) { for(; beg != end; ++beg) { cout << vec[beg]->val << " "; if (vec[beg]->left != NULL) vec.push_back(vec[beg]->left); if (vec[beg]->right != NULL) vec.push_back(vec[beg]->right); } } else { for(int j = beg, k = end-1; k >= beg; ++j, --k) { cout << vec[k]->val << " "; if (vec[j]->left != NULL) vec.push_back(vec[j]->left); if (vec[j]->right != NULL) vec.push_back(vec[j]->right); } beg = end; } end = vec.size(); L2R ^= true; cout << " --------------" << endl; } } int main() { TreeNode *root = new TreeNode(0); TreeNode *p1 = new TreeNode(1); TreeNode *p2 = new TreeNode(2); root->left = p1; root->right = p2; TreeNode *p3 = new TreeNode(3); TreeNode *p4 = new TreeNode(4); p1->left = p3; p1->right = p4; TreeNode *p5 = new TreeNode(5); TreeNode *p6 = new TreeNode(6); p2->left = p5; p2->right = p6; TreeNode *p7 = new TreeNode(7); TreeNode *p8 = new TreeNode(8); p3->left = p7; p3->right = p8; TreeNode *p9 = new TreeNode(9); p4->right = p9; LevelTranverse(root); }