1、题目:输入一个整数和一棵二元树。
从树的根结点开始往下访问一直到叶结点所经过的所有结点形成一条路径。
打印出和与输入整数相等的所有路径。
例如 输入整数22和如下二元树
10
/ \
5 12
/ \
4 7
则打印出两条路径:10, 12和10, 5, 7。
二元树节点的数据结构定义为:
struct BinaryTreeNode // a node in the binary tree
{
int m_nValue; // value of node
BinaryTreeNode *m_pLeft; // left child of node
BinaryTreeNode *m_pRight; // right child of node
};
2、知识点:栈,树,遍历
3、思路:我用后序遍历的显示栈实现,比较复杂。
/*用途:
**说明:
**算法:
*/
//#define LOCAL
#include <cstdio>
#include <cstdlib>
#include <stack>
using namespace std;
struct BinaryTreeNode // a node in the binary tree
{
int m_nValue; // value of node
BinaryTreeNode *m_pLeft; // left child of node
BinaryTreeNode *m_pRight; // right child of node
};
typedef BinaryTreeNode* BST;
BinaryTreeNode* NewNode();
BinaryTreeNode* NewNode(int v);
void PrintPaths(BST bst, int val);
void PrintStack(stack<BinaryTreeNode*> s);
int main()
{
BST bst = NewNode();
BinaryTreeNode *n0 = NewNode(10);
bst->m_pLeft = n0;
BinaryTreeNode *n1 = NewNode(5);
n0->m_pLeft = n1;
BinaryTreeNode *n2 = NewNode(12);
n0->m_pRight = n2;
BinaryTreeNode *n3 = NewNode(4);
n1->m_pLeft = n3;
BinaryTreeNode *n4 = NewNode(7);
n1->m_pRight = n4;
int val = 22;
PrintPaths(bst, val);
return 0;
}
BinaryTreeNode* NewNode()
{
BinaryTreeNode* pNode = (BinaryTreeNode*)malloc(sizeof(BinaryTreeNode));
pNode->m_pLeft = pNode->m_pRight = NULL;
return pNode;
}
BinaryTreeNode* NewNode(int v)
{
BinaryTreeNode* pNode = (BinaryTreeNode*)malloc(sizeof(BinaryTreeNode));
pNode->m_nValue = v;
pNode->m_pLeft = pNode->m_pRight = NULL;
return pNode;
}
void PrintPaths(BST bst, int val)
{
stack<BinaryTreeNode*> s;
stack<char> sc; //记录往哪个方向走
char c;
BinaryTreeNode* p = bst->m_pLeft;
int tot = 0;
while(!s.empty() || p){ //后序遍历
if(p){
tot += p->m_nValue;
s.push(p);
sc.push('L');
p = p->m_pLeft;
if(tot == val)
PrintStack(s);
}
else{
c = sc.top();
sc.pop();
if(c == 'L'){ //左儿子为空,访问右儿子
p = s.top();
p = p->m_pRight;
sc.push('R');
}
else{ //右儿子为空,访问双亲节点
while(!sc.empty()){ //直至找到最近左分支
p = s.top();
s.pop();
tot -= p->m_nValue;
c = sc.top();
if(c == 'L')
break;
sc.pop();
}
if(sc.empty()){
p = s.top(); //打印根节点,返回
s.top();
tot -= p->m_nValue;
return;
}
p = s.top(); //访问左分支结点右儿子
p = p->m_pRight;
sc.pop();
sc.push('R');
}
}
}
}
void PrintStack(stack<BinaryTreeNode*> s)
{
stack<BinaryTreeNode*> sr;
while(!s.empty()){
sr.push(s.top());
s.pop();
}
while(!sr.empty()){
BinaryTreeNode* pNode = sr.top();
printf("%d ", pNode->m_nValue);
sr.pop();
}
printf("\n");
}