Offer 驾到,掘友接招!我正在参与2022春招系列活动-刷题打卡任务,点击查看活动详情。
一、题目描述
给定一个二叉搜索树 root 和一个目标结果 k,如果 BST 中存在两个元素且它们的和等于给定的目标结果,则返回 true。
示例
示例1:
输入: root = [5,3,6,2,4,null,7], k = 9
输出: true
示例2:
输入: root = [5,3,6,2,4,null,7], k = 28
输出: false
提示
- 二叉树的节点个数的范围是
[1, 104]. -104 <= Node.val <= 104root为二叉搜索树-105 <= k <= 105
难度:简单
二、思路分析
众所周知,力扣上,简单题是真简单,中等题有些困难,困难题看不懂答案。 此题为简单题,兄弟们可以重拳出击,没错,就是你想到的那种方法,简单粗暴!
题目解析
- BST,即二叉搜索树,二叉搜索树的特点就是任何一个结点的左子结点总是小于于自身值,右子结点总是大于自身值。
- 如果是在数组中,可以使用遍历方法来判断是否存在符合要求的元素,或者将数组中元素排序后使用左右指针来判断是否存在,因此我们只需要将 BST 转成有序数组,即可通过双指针方法判断结果。
- 二叉搜索树 BST 的中序遍历结果得到一个有序集合。
解题思路
通过对题目解析,可以得到如下的题目解答流程
- 定义一个集合用来存放二叉搜索树中序遍历的序列值
- 使用递归方法中序遍历二叉搜索树,结点值放入全局集合中,遍历完成得到一个有序集合
- 定义左右两个指针,分别指向集合两端的最大值和最小值,并不断进行以下判断
- 如果当前指向的两数之和等于目标值,则直接返回 true;
- 如果当前指向的两数之和小于目标值,则左侧指针向右移动一位;
- 如果当前指向的两数之和大于目标值,则右侧指针向左移动一位;
- 如果左指针位置大于等于右指针位置,说明已经判断所有数字,此时并没有发现等于目标值的两数;
- 如果程序正常执行结束,则返回false。
三、AC 代码
class Solution {
List<Integer> list;
public boolean findTarget(TreeNode root, int k) {
list = new ArrayList<>();
// 中序递归遍历 BST,得到有序集合
getNodeValue(root);
// 使用双指针在有序集合中求解两数之和
int l = 0, r = list.size()-1;
while(l < r){
int sum = list.get(l) + list.get(r);
if(sum == k) return true;
if(sum < k) l++;
else r--;
}
return false;
}
public void getNodeValue(TreeNode root){
if(root == null) return ;
if(root.left != null) getNodeValue(root.left);
list.add(root.val);
if(root.right != null) getNodeValue(root.right);
}
}
- 执行用时:2 ms, 在所有 Java 提交中击败了97.52%的用户
- 内存消耗:42.1 MB, 在所有 Java 提交中击败了17.12%的用户
- 通过测试用例:422 / 422
四、总结
知识点
- BST,二叉搜索树,其中任意结点满足:左子结点比根结点更小,右子结点比根结点更大,其中序遍历得到非减序列
- 有序数组的判断是否存在两数之和满足目标值,使用左右双指针方法
最后
阳春三月,算法刷起来!LeetCode 每日一题。
简单题,不需要考虑太多,开干就是了。