题目描述:
输入一个整数数组,判断该数组是不是某二叉搜索树的前序和后序遍历的结果。如果是则输出Yes,否则输出No。假设输入的数组的任意两个数字都互不相同。
二叉搜索树:空树或者二叉树的所有结点比它的左子结点大,比它的右子结点小。
举例:
一、前序遍历:
思路:前序遍历的方法是,先遍历根节点,在遍历其根的左孩子,再是右孩子;以此类推,以上图为例,前序遍历的结果是:【12,5,2,9,18,15,17,16,19】
核心是前序遍历的第一个一定是根节点,利用二叉搜索树的性质可将其分为两部分,小于根的和大于根的。以此递归判断。
实现代码如下:
1 public class Solution {
2 public boolean VerifySquenceOfBST(int [] sequence) {
3 if(sequence.length == 0){
4 return false;
5 }
6 return isTrueBTS(sequence,0,sequence.length -1);
7 }
8
9 public boolean isTrueBTS(int []sequence,int start,int end){
10 if(end <= start) return true;
11 int i = start;
12 for(;i < end ; i++){
13 //数组的第一个一定是根节点,左孩子一定小于根,右孩子一定大于根
14 //定第一个,分成两部分,这一部分是前部分比它小的
15 if(sequence[i] > sequence[start]) break;
16 }
17 for(int j = i;j < end ; j++){
18 //数组的最后一个一定是根节点
19 //定最后一个,分成两部分,这是后面比它大的
20 if(sequence[j] < sequence[start]) return false;
21 }
22 return (isTrueBTS(sequence,start,i-1) &&
23 isTrueBTS(sequence,i,end - 1));
24 }
25 }
注意:判断前部分的if条件中,只要是第一个和前部分后面的比较出现比第一个大的就跳出循环从下一个作为第一个继续判断。
二、后序遍历:
思路:后序遍历的方法是,先遍历左孩子,再是右孩子,最后是其根节点;以此类推,以上图为例,后序遍历的结果是:【2,9,5,16,17,15,19,18,12】
核心是后序遍历的最后一个一定是根节点,利用二叉搜索树的性质可将其分为两部分,小于根的和大于根的。以此递归判断。
实现代码如下:
1 public class Solution {
2 public boolean VerifySquenceOfBST(int [] sequence) {
3 if(sequence.length == 0){
4 return false;
5 }
6 return isTrueBTS(sequence,0,sequence.length -1);
7 }
8
9 public boolean isTrueBTS(int []sequence,int start,int end){
10 if(end <= start) return true;
11 int i = start;
12 for(;i < end ; i++){
13 //数组的最后一个一定是根节点,左孩子一定小于根,右孩子一定大于根
14 //定最后一个,分成两部分,前半部分一定是左边比根小
15 //这就是前面的一部分
16 if(sequence[i] > sequence[end]) break;
17 }
18 for(int j = i;j < end ; j++){
19 //数组的最后一个一定是根节点
20 //定最后一个,分成两部分,后部分的一定是右边的比根大
21 //这就是后面的一部分
22 if(sequence[j] < sequence[end]) return false;
23 }
24 return (isTrueBTS(sequence,start,i-1) &&
25 isTrueBTS(sequence,i,end - 1));
26 }
27 }