【题目要求】
给定一棵二叉树,要求从下至上按层遍历二叉树输出遍历序列。访问次序是从下到上,每层的访问顺序是从左到右。
【输入输出】
输入用前序遍历序列表示的二叉树。
输出二叉树按照从下至上,从左到右访问的遍历序列。元素间以空格隔开。
【样例输入】
ab##cd##e##
【样例输出】
d e b c a
【代码】
【解法一】
#include<iostream>
#include<stdio.h>
#include<queue>
#include<stack>
using namespace std;
struct BiNode
{
char data;//数据域
BiNode* lchild, * rchild;//左右儿子指针
};
struct QNode
{
BiNode* pNode;
int levelNum; //记录当前层数
};
class BiTree {
private:
BiNode* root; //指向根结点的头指针
public:
BiTree()
{
root = creat(root);//调函数构建二叉树
}
~BiTree() {
release(root);
}
BiNode* getRoot() { return root; }
BiNode* creat(BiNode* bt); //构造函数调用
void release(BiNode* bt); //析构函数调用,释放树的存储空间
void reverseLeverOrder(BiNode* bt);//层序遍历函数调用
};
//前序构建二叉树
BiNode* BiTree::creat(BiNode* bt)
{
char ch;
cin >> ch;
if (ch == '#')
bt = NULL;
else
{
bt = new BiNode;
bt->data = ch;
bt->lchild = creat(bt->lchild);
bt->rchild = creat(bt->rchild);
}
return bt;
}
//层序遍历
void BiTree::reverseLeverOrder(BiNode* bt)
{
queue<QNode> Q;
stack<char> stack1; //存放结果
stack<char> stack2; //临时堆栈,用来给每层反序
QNode cur;
int curLevel = 1; //当前正在处理的层号
//将根节点包括层号入队
cur.pNode = bt;
cur.levelNum = 1;
Q.push(cur); //入队
//按层序遍历二叉树
while (!Q.empty())
{
//队首元素出队
QNode cur = Q.front();
Q.pop();
int levelNum = cur.levelNum;
//进入下一层,把stack2中的数据一次弹出,压入stack1
if (curLevel != levelNum)
{
while (!stack2.empty())
{
char ch = stack2.top();
stack2.pop();
stack1.push(ch);
curLevel = levelNum;
}
}
stack2.push(cur.pNode->data);
if (cur.pNode->lchild)
{
QNode tmp;
tmp.pNode = cur.pNode->lchild;
tmp.levelNum = levelNum + 1;
Q.push(tmp); //左孩子入栈
}
if (cur.pNode->rchild)
{
QNode tmp;
tmp.pNode = cur.pNode->rchild;
tmp.levelNum = levelNum + 1;
Q.push(tmp); //右孩子入栈
}
}
while (!stack2.empty())
{
char ch = stack2.top();
stack2.pop();
stack1.push(ch);
}
while (!stack1.empty())
{
cout << stack1.top() << " ";
stack1.pop();
}
}
//析构函数
void BiTree::release(BiNode* bt)
{
if (bt != NULL)
{
release(bt->lchild);
release(bt->rchild);
// cout<<"delete "<<bt->data<<endl;
delete bt;
}
}
int main()
{
cout<<"输入前序字符串:";
BiTree tree;
cout << "层序遍历二叉树" << endl;
tree.reverseLeverOrder(tree.getRoot());
tree.release(tree.getRoot());
return 0;
}
【解法二】
#include<iostream>
#include<stdio.h>
#include<queue>
#include<stack>
using namespace std;
struct BiNode
{
char data;//数据域
BiNode* lchild, * rchild;//左右儿子指针
};
struct QNode
{
BiNode* pNode;
int levelNum; //记录当前层数
};
class BiTree {
private:
BiNode* root; //指向根结点的头指针
public:
BiTree()
{
root = creat(root);//调函数构建二叉树
}
~BiTree() {
release(root);
}
BiNode* getRoot() { return root; }
BiNode* creat(BiNode* bt); //构造函数调用
void release(BiNode* bt); //析构函数调用,释放树的存储空间
void reverseLeverOrder(BiNode* bt);//层序遍历函数调用
void leverOrder(BiNode* bt);
};
//前序构建二叉树
BiNode* BiTree::creat(BiNode* bt)
{
char ch;
cin >> ch;
if (ch == '#')
bt = NULL;
else
{
bt = new BiNode;
bt->data = ch;
bt->lchild = creat(bt->lchild);
bt->rchild = creat(bt->rchild);
}
return bt;
}
//层序遍历
void BiTree::reverseLeverOrder(BiNode* bt)
{
BiNode* q;
queue<BiNode*> Q;
stack<char> R;
Q.push(root);
if (root == NULL)
return;
while (!Q.empty())
{
q = Q.front();
R.push(q->data);
Q.pop();
//先压入右子树,再压入左子树
if (q->rchild != NULL)
Q.push(q->rchild);
if (q->lchild != NULL)
Q.push(q->lchild);
}
while (!R.empty())
{
cout << R.top()<<" ";
R.pop();
}
}
//析构函数
void BiTree::release(BiNode* bt)
{
if (bt != NULL)
{
release(bt->lchild);
release(bt->rchild);
// cout<<"delete "<<bt->data<<endl;
delete bt;
}
}
//层序遍历
void BiTree::leverOrder(BiNode* bt)
{
BiNode* q;
queue<BiNode*> Q;
Q.push(root);
if (root == NULL)
return;
while (!Q.empty())
{
q = Q.front();
cout << q->data;
Q.pop();
if (q->lchild != NULL)
Q.push(q->lchild);
if (q->rchild != NULL)
Q.push(q->rchild);
}
}
int main()
{
cout<<"输入前序字符串:";
BiTree tree;
cout << "层序遍历二叉树" << endl;
//tree.leverOrder(tree.getRoot()); cout << endl;
tree.reverseLeverOrder(tree.getRoot());
tree.release(tree.getRoot());
return 0;
}