输入一个整数数组,判断该数组是不是某二叉搜索树的后序遍历的结果。
如果是则输出Yes,否则输出No。假设输入的数组的任意两个数字都互不相同。
public class Solution {
public static void main(String[] args)
{
int[] sequence= {12,14,13,10};
System.out.print(new Solution().VerifySquenceOfBST(sequence));
}
/***********
* 二叉搜索树、二叉查找树 从根节点开始 左孩子节点值均小于根节点值小于右孩子节点值
* 判断思路:从最后一个元素开始比较 看能否将数组分成大于左边小于最后一个元素 右边大于最后一个元素的两部分
* 然后再去判断这两部分是否是二叉搜索树的后续遍历结果
* @param sequence 后续遍历的数组
* @return 是否符合二叉搜索树后序遍历序列的定义
*/
public boolean VerifySquenceOfBST(int [] sequence) {
//非空检测
if(sequence==null)
{
return false;
}
return partSequenceOfBST(sequence, 0, sequence.length-1);
}
/********************
* 判断数组的一部分是否是二叉搜索树的后序遍历序列
* @param sequence 需要进行判断的源数组
* @param start 判断数组起始位置
* @param end 判断数组的根节点位置
* @return 返回该部分是否是二叉搜索树的后序遍历序列
*/
public boolean partSequenceOfBST(int[] sequence,int start,int end)
{
//递归出口 start==end时,只剩一个元素时,是递归序列
//start>end时 说明子树中没有元素 即子树不存在
if(start>=end)
{
return true;
}
//从前向后查找左侧小于根节点的部分
int curIndex=0;//当前判断位置下标
while(curIndex<end)
{
//查找到大于根节点的位置 说明进入根节点右子树部分
if(sequence[curIndex]>sequence[end])
break;
curIndex++;
}
int leftTreeEndIndex=curIndex-1;
//遍历完成后 curIndex即为右子树开始位置
while(curIndex<end)
{
//右子树中出现了小于根节点的值
if(sequence[curIndex]<sequence[end])
return false;
curIndex++;
}
//如果右子树遍历循环正常跳出
//判断左右子树是否是二叉搜索序列
return partSequenceOfBST(sequence, start, leftTreeEndIndex)&&partSequenceOfBST(sequence, leftTreeEndIndex+1, end-1);
}
非递归方式检测二叉搜索树的后续遍历序列
/*********************
* 判断一个数组是否是二叉搜索树的后序遍历序列 ---非递归方式
* 对于递归的方式 是通过查找每一个节点是否具有小于此节点的左子树和右子树 先判断根节点 再左右节点的形式,左右节点之间没有先后顺序
* 而我们发现每一次判断时 子树的根节点位置都在序列的最右端
* 如果我们递归时左右节点采取先右后左的形式 会发现开始判断的均为序列的最后并向前递增 只是判断时的开始位置不是从头 而是从子树开始位置
* 但是在二叉搜索树的后序序列中 左子树的值恒小于右子树 对于序列中的一个根节点而言 他的左子树后序序列和左子树之前的值肯定是小于根节点值的
* 因为左子树之前的值为根节点父节点的左子树或者根节点
* @param sequence 后续遍历的数组
* @return 是否符合二叉搜索树后序遍历序列的定义
*/
public boolean verifySquenceOfBST(int[] sequence)
{
//非空判断
if(sequence==null||sequence.length==0)
{
return false;
}
//数组末位置下标
int endIndex=sequence.length-1;
while(endIndex>=0)
{
int i=0;
while(sequence[i]<sequence[endIndex]) i++;//查找左子树结束位置
while(sequence[i]>sequence[endIndex]) i++;//查找右子树结束位置
if(i<endIndex)//右子树中出现小于根节点的值
return false;
endIndex--;
}
return true;
}