654.最大二叉树
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {number[]} nums
* @return {TreeNode}
*/
var constructMaximumBinaryTree = function (nums) {
if (nums.length === 0) return null
let m = Math.max(...nums);
let x = nums.indexOf(m)
const root = new TreeNode(m, constructMaximumBinaryTree(nums.slice(0, x)), constructMaximumBinaryTree(nums.slice(x + 1))); // 创建中间节点
return root
};
第一想法
如代码
困难
- slice的左右区间注意,[ , ),左闭右开
617.合并二叉树
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root1
* @param {TreeNode} root2
* @return {TreeNode}
*/
var mergeTrees = function(root1, root2) {
if (root1 == null && root2) { //1不行 2行,直接返回2,不进行后面的节点相加操作了
return root2;
}
if ((root1 && root2 == null) || (root1 == null && root2 == null)) { //1行2不行,返回1;或者都不行,返回1也就是null
return root1;
}
//都行
const root =new TreeNode(root1.val+root2.val, mergeTrees(root1.left,root2.left),mergeTrees(root1.right,root2.right)) // 创建中间节点
return root
};
第一想法
递归
const root =new TreeNode(root1.val+root2.val,
mergeTrees(root1.left,root2.left),
mergeTrees(root1.right,root2.right)) // 创建中间节点
return root
困难
- 结束条件
if (root1 == null && root2) {
//1不行 2行,直接返回2,不进行后面的节点相加操作了
return root2;
}
if ((root1 && root2 == null) || (root1 == null && root2 == null)) {
//1行2不行,返回1;或者都不行,返回1也就是null
return root1;
}
700.二叉搜索树中的搜索
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @param {number} val
* @return {TreeNode}
*/
var searchBST = function(root, val) { //自己的写法
if(!root) return null;
const st=[root] //栈,pop(),push()
while(st.length){ //
let x=st.pop(); //每次遍历输出,把右左孩子入栈
if(x.val===val)
return x
x.right &&st.push(x.right) //很重要,不然下一次遍历x.val会出错
x.left &&st.push(x.left)
}
return null
};
**********************************************
var searchBST = function(root, val) {
while (root) {
if (val === root.val) {
return root;
}
root = val < root.val ? root.left : root.right;
}
return null;
};
//作者:迭代法力扣官方题解
***********************************************
var searchBST = function(root, val) {
if (!root) {
return null;
}
if (val === root.val) {
return root;
}
return searchBST(val < root.val ? root.left : root.right, val);
};
//作者:回调法力扣官方题解
第一想法
前序遍历就行了,不管是迭代法还是回调法,但是忽略了题目中的搜索树的条件。
思想
因为是搜索树,所以只有一条路径
98.验证二叉搜索树
法一:
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {boolean}
*/
var isValidBST = function(root) {
let arr = [];
const buildArr = function(root) {
if (root) {
buildArr(root.left);
arr.push(root.val);
buildArr(root.right);
}
}
buildArr(root);
for (let i = 1; i < arr.length; ++i) {
if (arr[i] <= arr[i - 1])
return false;
}
return true;
};
第一想法
先序遍历,然后递归,写不出来,然后我又忽略了题意,即使按我的想法做出来,
也不符合题意:
有效 二叉搜索树定义如下:
节点的左子树只包含 小于 当前节点的数。
节点的右子树只包含 大于 当前节点的数。
所有左子树和右子树自身必须也是二叉搜索树。
思想
- 有效二叉树的中序遍历出来是从小到大的,(迭代、回调)转换为数组,然后比较
法二:
let pre = null;
var isValidBST = function (root) {
let pre = null;
const inOrder = (root) => {
if (root === null)
return true;
let left = inOrder(root.left); //左
// 中序遍历,验证遍历的元素是不是从小到大
if (pre !== null && pre.val >= root.val)
return false;
pre = root;
let right = inOrder(root.right);//右
return left && right;
}
return inOrder(root);
};
思想
-
确定递归函数,返回值以及参数
let pre = null; 用来记录前一个节点 -
确定终止条件
如果是空节点 是不是二叉搜索树呢?
是的,二叉搜索树也可以为空!
代码如下:
if (root == NULL) return true; -
确定单层递归的逻辑
中序遍历,一直更新maxVal,一旦发现maxVal >= root->val,就返回false,注意元素相同时候也要返回false。
回调法的过程:
使用一个节点(pre)来记录之前访问过的节点,判断依据是当前节点的val一定要大于pre.val。