二叉树的非递归遍历

来源:互联网 发布:下载淘宝app官方软件 编辑:程序博客网 时间:2024/05/16 23:01

二叉树的非递归遍历需要用到栈,三种遍历方法中最麻烦的是后序遍历,因为它需要访问根结点2次,故在第一次访问的时候需要标示它的访问状态。

#include <iostream>#include <stack>using namespace std;typedef struct _Tree{int data;struct _Tree *left;struct _Tree *right;} Tree;typedef struct _Visit {Tree *node;bool visited;//访问标志} Visit;void PrePrintTree(Tree *root) {if (NULL == root)return;Tree *p = root;stack<Tree*> stk;stk.push(p);while (!stk.empty()) {Tree *cur = stk.top();stk.pop();cout << cur->data << ' '; //先输出,再push右结点,push左结点(先pop左,再pop右,从而是先序遍历)if (cur->right != NULL)stk.push(cur->right);if (cur->left != NULL)stk.push(cur->left);}cout << endl;}void InPrintTree(Tree *root) {if (NULL == root)return;Tree *p = root;stack<Tree*> stk;while (p != NULL) {  //1. 一路将左结点push到栈中,相当于左结点优先处理过了stk.push(p);p = p->left;}while (!stk.empty()) {Tree *cur = stk.top();stk.pop();cout << cur->data << ' '; //2. 输出中间结点if (cur->right != NULL) { //3. 将右结点按步骤1处理cur = cur->right;while (cur != NULL) {stk.push(cur);cur = cur->left;}}}cout << endl;}void PostPrintTree(Tree *root) {if (NULL == root)return;Tree *p = root;stack<Visit> stk;while (p != NULL) {  //1. 一路将左结点push到栈中,相当于左结点优先处理过了Visit v = {p, false};stk.push(v);p = p->left;}while (!stk.empty()) {Visit cur = stk.top();stk.pop();//2. 当前结点是第一次访问,且有右结点没有处理,则修改访问标志,再次push当前结点//然后按步骤1处理当前结点的右结点if (cur.node->right != NULL && cur.visited == false) {Visit v = {cur.node, true}; //修改访问标志为true,再次push当前结点stk.push(v);p = cur.node->right;while (p != NULL) {Visit v = {p, false};stk.push(v);p = p->left;}} else {cout << cur.node->data << ' '; //3. 当前结点处理后,输出}}cout << endl;}int main(){Tree a1 = {1, NULL, NULL};Tree a2 = {2, NULL, NULL};Tree a3 = {3, NULL, NULL};Tree a4 = {4, NULL, NULL};Tree a5 = {5, &a1, &a2};Tree a6 = {6, &a3, &a4};Tree a7 = {7, &a5, &a6};PrePrintTree(&a7);InPrintTree(&a7);PostPrintTree(&a7);return 0;}

输出:

7 5 1 2 6 3 4
1 5 2 7 3 6 4
1 2 5 3 4 6 7