五道题

This commit is contained in:
游由 2022-02-10 14:22:48 +08:00
parent bd02130ba1
commit 5df97bae16
7 changed files with 381 additions and 17 deletions

View File

@ -22,8 +22,11 @@ mod q0087;
mod q0090;
mod q0091;
mod q0094;
mod q0100;
mod q0101;
mod q0102;
mod q0110;
mod q0111;
mod q0118;
mod q0119;
mod q0121;
@ -63,6 +66,7 @@ mod q0375;
mod q0377;
mod q0392;
mod q0403;
mod q0404;
mod q0405;
mod q0407;
mod q0412;
@ -107,3 +111,4 @@ mod q1486;
mod q1720;
mod q1723;
mod q1734;
mod q2006;

View File

@ -0,0 +1,81 @@
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
impl Solution {
/// [100.相同的树](https://leetcode-cn.com/problems/same-tree/)
///
/// 2022-02-09 16:05:06
///
/// 给你两棵二叉树的根节点 `p` 和 `q` ,编写一个函数来检验这两棵树是否相同。
///
/// 如果两个树在结构上相同,并且节点具有相同的值,则认为它们是相同的。
///
/// + **示例 1**
/// + ![](https://assets.leetcode.com/uploads/2020/12/20/ex1.jpg)
/// + **输入:**p = \[1,2,3\], q = \[1,2,3\]
/// + **输出:**true
/// + **示例 2**
/// + ![](https://assets.leetcode.com/uploads/2020/12/20/ex2.jpg)
/// + **输入:**p = \[1,2\], q = \[1,null,2\]
/// + **输出:**false
/// + **示例 3**
/// + ![](https://assets.leetcode.com/uploads/2020/12/20/ex3.jpg)
/// + **输入:**p = \[1,2,1\], q = \[1,1,2\]
/// + **输出:**false
/// + **提示:**
/// * 两棵树上的节点数目都在范围 `[0, 100]` 内
/// * `-104 <= Node.val <= 104`
/// + Related Topics
/// * 树
/// * 深度优先搜索
/// * 广度优先搜索
/// * 二叉树
///
/// * 👍 761
/// * 👎 0
pub fn is_same_tree(p: Option<Rc<RefCell<TreeNode>>>, q: Option<Rc<RefCell<TreeNode>>>) -> bool {
match (p, q) {
(Some(l), Some(r)) => {
let (mut a, mut b) = (l.borrow_mut(), r.borrow_mut());
a.val == b.val && Self::is_same_tree(a.left.take(), b.left.take()) && Self::is_same_tree(a.right.take(), b.right.take())
}
(Some(_), None) => false,
(None, Some(_)) => false,
_ => true,
}
}
}
#[cfg(test)]
mod test {
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
#[test]
fn test_q0100() {
let p = Some(Rc::new(RefCell::new(TreeNode {
val: 1,
left: None,
right: Some(Rc::new(RefCell::new(TreeNode {
val: 3,
left: Some(Rc::new(RefCell::new(TreeNode::new(3)))),
right: None,
}))),
})));
let q = Some(Rc::new(RefCell::new(TreeNode {
val: 1,
left: None,
right: Some(Rc::new(RefCell::new(TreeNode {
val: 3,
left: Some(Rc::new(RefCell::new(TreeNode::new(4)))),
right: None,
}))),
})));;
assert_eq!(Solution::is_same_tree(p, q), false);
}
}

View File

@ -0,0 +1,80 @@
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
impl Solution {
/// [110.平衡二叉树](https://leetcode-cn.com/problems/balanced-binary-tree/)
///
/// 2022-02-09 16:37:47
///
/// 给定一个二叉树,判断它是否是高度平衡的二叉树。
///
/// 本题中,一棵高度平衡二叉树定义为:
///
/// > 一个二叉树_每个节点_ 的左右两个子树的高度差的绝对值不超过 1 。
///
/// + **示例 1**
/// + ![](https://assets.leetcode.com/uploads/2020/10/06/balance_1.jpg)
/// + **输入:** root = \[3,9,20,null,null,15,7\]
/// + **输出:** true
/// + **示例 2**
/// + ![](https://assets.leetcode.com/uploads/2020/10/06/balance_2.jpg)
/// + **输入:** root = \[1,2,2,3,3,null,null,4,4\]
/// + **输出:** false
/// + **示例 3**
/// + **输入:** root = \[\]
/// + **输出:** true
/// + **提示:**
/// * 树中的节点数在范围 `[0, 5000]` 内
/// * `-104 <= Node.val <= 104`
/// + Related Topics
/// * 树
/// * 深度优先搜索
/// * 二叉树
/// * 👍 881
/// * 👎 0
pub fn is_balanced(root: Option<Rc<RefCell<TreeNode>>>) -> bool {
pub fn balanced(root: &Option<Rc<RefCell<TreeNode>>>) -> i32 {
match root {
Some(node) => {
let left_h = balanced(&node.borrow().left);
if left_h == -1 {
return -1;
}
let right_h = balanced(&node.borrow().right);
if right_h == -1 || (left_h - right_h).abs() > 1 {
return -1;
}
left_h.max(right_h) + 1
}
_ => 0
}
}
balanced(&root) != -1
}
}
#[cfg(test)]
mod test {
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
#[test]
fn test_q0110() {
let a = (|a: i32, b: i32| -> i32 { a + b })(1, 2);
let tree = Some(Rc::new(RefCell::new(TreeNode {
val: 3,
left: Some(Rc::new(RefCell::new(TreeNode::new(9)))),
right: Some(Rc::new(RefCell::new(TreeNode {
val: 20,
left: Some(Rc::new(RefCell::new(TreeNode::new(15)))),
right: Some(Rc::new(RefCell::new(TreeNode::new(7)))),
}))),
})));
assert_eq!(Solution::is_balanced(tree), true);
}
}

View File

@ -0,0 +1,70 @@
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
impl Solution {
/// [111.二叉树的最小深度](https://leetcode-cn.com/problems/minimum-depth-of-binary-tree/)
///
/// 2022-02-09 17:11:54
/// 给定一个二叉树,找出其最小深度。
///
/// 最小深度是从根节点到最近叶子节点的最短路径上的节点数量。
///
/// + **说明:** 叶子节点是指没有子节点的节点。
/// + **示例 1**
/// + ![](https://assets.leetcode.com/uploads/2020/10/12/ex_depth.jpg)
/// + **输入:** root = \[3,9,20,null,null,15,7\]
/// + **输出:** 2
/// + **示例 2**
/// + **输入:** root = \[2,null,3,null,4,null,5,null,6\]
/// + **输出:** 5
/// + **提示:**
/// * 树中节点数的范围在 `[0, 105]` 内
/// * `-1000 <= Node.val <= 1000`
/// + Related Topics
/// * 树
/// * 深度优先搜索
/// * 广度优先搜索
/// * 二叉树
/// * 👍 666
/// * 👎 0
pub fn min_depth(root: Option<Rc<RefCell<TreeNode>>>) -> i32 {
match root {
Some(node) => {
let mut p = node.borrow_mut();
if p.left.is_none() {
Self::min_depth(p.right.take()) + 1
} else if p.right.is_none() {
Self::min_depth(p.left.take()) + 1
} else {
Self::min_depth(p.left.take()).min(Self::min_depth(p.right.take())) + 1
}
}
_ => 0
}
}
}
#[cfg(test)]
mod test {
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
#[test]
fn test_q0111() {
let tree = Some(Rc::new(RefCell::new(TreeNode {
val: 4,
left: Some(Rc::new(RefCell::new(TreeNode::new(9)))),
right: Some(Rc::new(RefCell::new(TreeNode {
val: 10,
left: Some(Rc::new(RefCell::new(TreeNode::new(15)))),
right: Some(Rc::new(RefCell::new(TreeNode::new(7)))),
}))),
})));
assert_eq!(Solution::min_depth(tree), 2);
}
}

View File

@ -0,0 +1,78 @@
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
impl Solution {
/// [404.左叶子之和](https://leetcode-cn.com/problems/sum-of-left-leaves/)
///
/// 2022-02-09 17:40:54
///
/// 计算给定二叉树的所有左叶子之和。
///
/// **示例:**
///
/// ```txt
/// 3
/// / \
/// 9 20
/// / \
/// 15 7
/// ```
/// 在这个二叉树中,有两个左叶子,分别是 9 和 15所以返回 24
///
/// + Related Topics
/// * 树
/// * 深度优先搜索
/// * 广度优先搜索
/// * 二叉树
/// * 👍 392
/// * 👎 0
pub fn sum_of_left_leaves(root: Option<Rc<RefCell<TreeNode>>>) -> i32 {
fn is_leaf_node(node:&Option<Rc<RefCell<TreeNode>>>) -> bool {
let n = node.as_ref().unwrap().borrow();
n.left.is_none() && n.right.is_none()
}
let mut ans = 0;
match root {
Some(node) => {
let mut p = node.borrow_mut();
if p.left.is_some() {
ans += if is_leaf_node(&p.left) {
p.left.as_ref().unwrap().borrow().val
} else {
Self::sum_of_left_leaves(p.left.take())
};
}
if p.right.is_some() && ! is_leaf_node(&p.right) {
ans += Self::sum_of_left_leaves(p.right.take());
}
}
_ => ()
}
ans
}
}
#[cfg(test)]
mod test {
use crate::Solution;
use crate::structure::TreeNode;
use std::rc::Rc;
use std::cell::RefCell;
#[test]
fn test_q0404() {
let tree = Some(Rc::new(RefCell::new(TreeNode {
val: 3,
left: Some(Rc::new(RefCell::new(TreeNode::new(9)))),
right: Some(Rc::new(RefCell::new(TreeNode {
val: 21,
left: Some(Rc::new(RefCell::new(TreeNode::new(15)))),
right: Some(Rc::new(RefCell::new(TreeNode::new(7)))),
}))),
})));
assert_eq!(Solution::sum_of_left_leaves(tree), 24);
}
}

View File

@ -0,0 +1,67 @@
use crate::Solution;
impl Solution {
/// [2006.差的绝对值为 K 的数对数目](https://leetcode-cn.com/problems/count-number-of-pairs-with-absolute-difference-k/)
///
/// 2022-02-09 10:02:13
///
/// 给你一个整数数组 `nums` 和一个整数 `k` ,请你返回数对 `(i, j)` 的数目,满足 `i < j` 且 `|nums[i] - nums[j]| == k` 。
///
/// + `|x|` 的值定义为:
/// * 如果 `x >= 0` ,那么值为 `x` 。
/// * 如果 `x < 0` ,那么值为 `-x` 。
/// + **示例 1**
/// + **输入:** nums = \[1,2,2,1\], k = 1
/// + **输出:** 4
/// + **解释:** 差的绝对值为 1 的数对为:
/// - \[_**1**_,_**2**_,2,1\]
/// - \[_**1**_,2,_**2**_,1\]
/// - \[1,_**2**_,2,_**1**_\]
/// - \[1,2,_**2**_,_**1**_\]
/// + **示例 2**
/// + **输入:** nums = \[1,3\], k = 3
/// + **输出:** 0
/// + **解释:** 没有任何数对差的绝对值为 3 。
/// + **示例 3**
/// + **输入:** nums = \[3,2,1,5,4\], k = 2
/// + **输出:** 3
/// + **解释:** 差的绝对值为 2 的数对为:
/// - \[_**3**_,2,_**1**_,5,4\]
/// - \[_**3**_,2,1,_**5**_,4\]
/// - \[3,_**2**_,1,5,_**4**_\]
/// + **提示:**
/// * `1 <= nums.length <= 200`
/// * `1 <= nums[i] <= 100`
/// * `1 <= k <= 99`
/// + Related Topics
/// * 数组
/// * 哈希表
/// * 计数
/// * 👍 26
/// * 👎 0
pub fn count_k_difference(nums: Vec<i32>, k: i32) -> i32 {
if nums.len() < 2 {
return 0;
}
let mut ans = 0;
for i in 0..nums.len() {
for j in (i + 1)..nums.len() {
if (nums[i] - nums[j]).abs() == k {
ans += 1;
}
}
}
ans
}
}
#[cfg(test)]
mod test {
use crate::Solution;
#[test]
fn test_q2006() {
assert_eq!(Solution::count_k_difference(vec![1, 2, 2, 1], 1), 4);
}
}

View File

@ -636,23 +636,6 @@ impl Solution {
solutions
}
/// 100.相同的树
///
/// [原题链接](https://leetcode-cn.com/problems/same-tree/)
/// todo
pub fn is_same_tree(p: Option<Rc<RefCell<TreeNode>>>, q: Option<Rc<RefCell<TreeNode>>>) -> bool {
match (p, q) {
(Some(r), Some(e)) => {
r.borrow().val == e.borrow().val
&& Solution::is_same_tree(r.borrow().left.clone(), e.borrow().left.clone())
&& Solution::is_same_tree(r.borrow().right.clone(), e.borrow().right.clone())
},
(Some(_r), None) => false,
(None, Some(_e)) => false,
_ => true,
}
}
/// 6.Z 字形变换
///
/// [原题链接](https://leetcode-cn.com/problems/zigzag-conversion/)