二叉树的遍历规则主要有三种:前序遍历,中序遍历,后序遍历。它们是根据访问根节点的先后顺序来划分的。
前序遍历:
1.访问根节点2.前序遍历左子树
3.右序遍历右子树
中序遍历:
1.中序遍历左子树2.访问根节点
3.中序遍历右子树
后序遍历:
1.后序遍历左子树2.后序遍历右子树
3.访问根节点
前序遍历: GDAFEMHZ
中序遍历: ADEFGHMZ
后序遍历: AEFDHZMG
前序遍历的特点:树的根节点位于所有它的子树节点之前。
中序遍历的特点:树的根节点的前面是它的左子树节点,它的后面是它的右子树节点。
后序遍历的特点:树的根节点位于最后一个位置。
问题1:已知前序遍历GDAFEMHZ和中序遍历ADEFGHMZ,求后序遍历?
1.前序遍历的特点是树的根节点位于所有它的子树节点之前,所以G是树根。2.中序遍历的特点:树的根节点的前面是它的左子树节点,它的后面是它的右子树节点。所以ADEF是G的左子树,HMZ是G的右子树。
3.在子树ADEF和子树HMZ中根据上面的思路可以判断各个节点的位置。
左子树ADEF中D是根节点,A是D的左节点,EF是D的右子树。F是E的父节点。
右子树HMZ中M是根节点,H是左节点,Z是右节点。
见图示:
问题2:已知后序遍历AEFDHZMG和中序遍历ADEFGHMZ,求前序遍历?
思路同上问。
见图示:
问题3:已知前序遍历GDAFEMHZ和后序遍历AEFDHZMG,求中序遍历?
1.由后序遍历的特点可以知道,G是根节点。由前序遍历的特点也可以知道G是根节点,并且可以知道D是左子树的根节点,再根据后序遍历可以知道AEFD是G的左子树节点。HZM是G的右子树节点。
2.后序遍历AEFD,前序遍历DAFE中,再根据上面的思路;
3.后序遍历HZM,前序遍历MHZ中,再根据上面的思路;
见图书:
如果是数学式子的情况,针对前两个问题除了画出二叉树的图形外还有简单的思路。
问题1.已知中序遍历:a+b*c-(d+e),求后序遍历?
首先将表达式按优先级加上括号,((a+(b*c))-(d+e))然后将上面运算式中的运算符放到对应括号的后面,结果是:((a+(b*c))-(d+e)) ---》((a(bc)*)+(de)+)-
最后将上面式子中的括号去掉:((a(bc)*)+(de)+)- ---》 abc*+de+-
问题2.已知中序遍历:a+b*c-(d+e),求前序遍历?
首先将表达式按优先级加上括号,((a+(b*c))-(d+e))然后将上面运算式中的运算符放到对应括号的前面,结果是:((a+(b*c))-(d+e)) ---》 -(+(a*(bc))+(de))
最后将上面式子中的括号去掉:-(+(a*(bc))+(de)) ---》 -+a*bc+de
但是对于问题3就稍微比较麻烦一点:
问题3:已知前序遍历(-+a*bc+de)和后序遍历(abc*+de+-)求中序列遍历?
思路1:可以根据之前问题3的思路画出二叉树的形状,但是比较麻烦。思路2:借鉴之前的思路,对于前序遍历-+a*bc+de 我们在每个运算符前面加上( , 得到 -(+(a*(bc+(de ,然后再适当的根据(进行配对,加上另一个括号)。
可以得到 -(+(a(b*c)(d+e) ,+(a(b*c) 得到 (a+(b*c)); -((a+(b*c))(d+e) 得到 (a+(b*c))-(d+e);
对于后序遍历abc*+de+- 我们在每个运算符的前面加上),得到abc)*)+de)+)- ;
题目的答案: