diff --git a/solution/0100-0199/0112.Path Sum/README_EN.md b/solution/0100-0199/0112.Path Sum/README_EN.md index b3df7020a512a..46aa820d83f3e 100644 --- a/solution/0100-0199/0112.Path Sum/README_EN.md +++ b/solution/0100-0199/0112.Path Sum/README_EN.md @@ -37,7 +37,7 @@ tags:
Input: root = [1,2,3], targetSum = 5 Output: false -Explanation: There two root-to-leaf paths in the tree: +Explanation: There are two root-to-leaf paths in the tree: (1 --> 2): The sum is 3. (1 --> 3): The sum is 4. There is no root-to-leaf path with sum = 5. diff --git a/solution/0400-0499/0442.Find All Duplicates in an Array/README_EN.md b/solution/0400-0499/0442.Find All Duplicates in an Array/README_EN.md index 3ece71c0a4ce0..013557eeb986e 100644 --- a/solution/0400-0499/0442.Find All Duplicates in an Array/README_EN.md +++ b/solution/0400-0499/0442.Find All Duplicates in an Array/README_EN.md @@ -17,7 +17,7 @@ tags: -Given an integer array
+numsof lengthnwhere all the integers ofnumsare in the range[1, n]and each integer appears once or twice, return an array of all the integers that appears twice.Given an integer array
numsof lengthnwhere all the integers ofnumsare in the range[1, n]and each integer appears at most twice, return an array of all the integers that appears twice.You must write an algorithm that runs in
diff --git a/solution/0800-0899/0887.Super Egg Drop/README.md b/solution/0800-0899/0887.Super Egg Drop/README.md index 3768e9efb584c..39d3803790ed8 100644 --- a/solution/0800-0899/0887.Super Egg Drop/README.md +++ b/solution/0800-0899/0887.Super Egg Drop/README.md @@ -158,7 +158,7 @@ public: int superEggDrop(int k, int n) { int f[n + 1][k + 1]; memset(f, 0, sizeof(f)); - functionO(n)time and uses only constant auxiliary space, excluding the space needed to store the outputdfs = [&](int i, int j) -> int { + auto dfs = [&](auto&& dfs, int i, int j) -> int { if (i < 1) { return 0; } @@ -171,17 +171,17 @@ public: int l = 1, r = i; while (l < r) { int mid = (l + r + 1) >> 1; - int a = dfs(mid - 1, j - 1); - int b = dfs(i - mid, j); + int a = dfs(dfs, mid - 1, j - 1); + int b = dfs(dfs, i - mid, j); if (a <= b) { l = mid; } else { r = mid - 1; } } - return f[i][j] = max(dfs(l - 1, j - 1), dfs(i - l, j)) + 1; + return f[i][j] = max(dfs(dfs, l - 1, j - 1), dfs(dfs, i - l, j)) + 1; }; - return dfs(n, k); + return dfs(dfs, n, k); } }; ``` diff --git a/solution/0800-0899/0887.Super Egg Drop/README_EN.md b/solution/0800-0899/0887.Super Egg Drop/README_EN.md index 42b7cac4045d2..3b1c934196d79 100644 --- a/solution/0800-0899/0887.Super Egg Drop/README_EN.md +++ b/solution/0800-0899/0887.Super Egg Drop/README_EN.md @@ -141,7 +141,7 @@ public: int superEggDrop(int k, int n) { int f[n + 1][k + 1]; memset(f, 0, sizeof(f)); - function dfs = [&](int i, int j) -> int { + auto dfs = [&](auto&& dfs, int i, int j) -> int { if (i < 1) { return 0; } @@ -154,17 +154,17 @@ public: int l = 1, r = i; while (l < r) { int mid = (l + r + 1) >> 1; - int a = dfs(mid - 1, j - 1); - int b = dfs(i - mid, j); + int a = dfs(dfs, mid - 1, j - 1); + int b = dfs(dfs, i - mid, j); if (a <= b) { l = mid; } else { r = mid - 1; } } - return f[i][j] = max(dfs(l - 1, j - 1), dfs(i - l, j)) + 1; + return f[i][j] = max(dfs(dfs, l - 1, j - 1), dfs(dfs, i - l, j)) + 1; }; - return dfs(n, k); + return dfs(dfs, n, k); } }; ``` diff --git a/solution/0800-0899/0887.Super Egg Drop/Solution.cpp b/solution/0800-0899/0887.Super Egg Drop/Solution.cpp index 0be08e60e0e5e..4fc7571df685d 100644 --- a/solution/0800-0899/0887.Super Egg Drop/Solution.cpp +++ b/solution/0800-0899/0887.Super Egg Drop/Solution.cpp @@ -3,7 +3,7 @@ class Solution { int superEggDrop(int k, int n) { int f[n + 1][k + 1]; memset(f, 0, sizeof(f)); - function dfs = [&](int i, int j) -> int { + auto dfs = [&](auto&& dfs, int i, int j) -> int { if (i < 1) { return 0; } @@ -16,16 +16,16 @@ class Solution { int l = 1, r = i; while (l < r) { int mid = (l + r + 1) >> 1; - int a = dfs(mid - 1, j - 1); - int b = dfs(i - mid, j); + int a = dfs(dfs, mid - 1, j - 1); + int b = dfs(dfs, i - mid, j); if (a <= b) { l = mid; } else { r = mid - 1; } } - return f[i][j] = max(dfs(l - 1, j - 1), dfs(i - l, j)) + 1; + return f[i][j] = max(dfs(dfs, l - 1, j - 1), dfs(dfs, i - l, j)) + 1; }; - return dfs(n, k); + return dfs(dfs, n, k); } -}; \ No newline at end of file +}; diff --git a/solution/3000-3099/3016.Minimum Number of Pushes to Type Word II/README_EN.md b/solution/3000-3099/3016.Minimum Number of Pushes to Type Word II/README_EN.md index 1d470861064a2..00e2e5513bf7f 100644 --- a/solution/3000-3099/3016.Minimum Number of Pushes to Type Word II/README_EN.md +++ b/solution/3000-3099/3016.Minimum Number of Pushes to Type Word II/README_EN.md @@ -49,7 +49,7 @@ It can be shown that no other mapping can provide a lower cost.
Example 2:
-
+
Input: word = "xyzxyzxyzxyz" Output: 12 diff --git a/solution/3000-3099/3095.Shortest Subarray With OR at Least K I/README_EN.md b/solution/3000-3099/3095.Shortest Subarray With OR at Least K I/README_EN.md index b61019222153c..8c710f1b490d9 100644 --- a/solution/3000-3099/3095.Shortest Subarray With OR at Least K I/README_EN.md +++ b/solution/3000-3099/3095.Shortest Subarray With OR at Least K I/README_EN.md @@ -37,6 +37,8 @@ tags:Explanation:
The subarray
+ +[3]hasORvalue of3. Hence, we return1.Note that
[2]is also a special subarray.Example 2:
diff --git a/solution/3300-3399/3314.Construct the Minimum Bitwise Array I/README_EN.md b/solution/3300-3399/3314.Construct the Minimum Bitwise Array I/README_EN.md index 676c8322e2a83..aeb5b42af38ba 100644 --- a/solution/3300-3399/3314.Construct the Minimum Bitwise Array I/README_EN.md +++ b/solution/3300-3399/3314.Construct the Minimum Bitwise Array I/README_EN.md @@ -22,8 +22,6 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3314.CoIf it is not possible to find such a value for
-ans[i]that satisfies the condition, then setans[i] = -1.A prime number is a natural number greater than 1 with only two factors, 1 and itself.
-
Example 1:
diff --git a/solution/3300-3399/3315.Construct the Minimum Bitwise Array II/README_EN.md b/solution/3300-3399/3315.Construct the Minimum Bitwise Array II/README_EN.md index 22efae3d6330f..f9ae16599b691 100644 --- a/solution/3300-3399/3315.Construct the Minimum Bitwise Array II/README_EN.md +++ b/solution/3300-3399/3315.Construct the Minimum Bitwise Array II/README_EN.md @@ -22,8 +22,6 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3315.CoIf it is not possible to find such a value for
-ans[i]that satisfies the condition, then setans[i] = -1.A prime number is a natural number greater than 1 with only two factors, 1 and itself.
-
Example 1:
diff --git a/solution/3300-3399/3316.Find Maximum Removals From Source String/README_EN.md b/solution/3300-3399/3316.Find Maximum Removals From Source String/README_EN.md index 59dba18f88d70..766fa13dabc9f 100644 --- a/solution/3300-3399/3316.Find Maximum Removals From Source String/README_EN.md +++ b/solution/3300-3399/3316.Find Maximum Removals From Source String/README_EN.md @@ -27,8 +27,6 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3316.FiReturn the maximum number of operations that can be performed.
-A subsequence is a string that can be derived from another string by deleting some or no characters without changing the order of the remaining characters.
-
Example 1:
diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README.md b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README.md index 296b8402b5da3..9334a995525d3 100644 --- a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README.md +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README.md @@ -83,32 +83,213 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3319.K- -### 方法一 +### 方法一:DFS + 排序 + +我们定义一个函数 $\textit{dfs}$,用于计算以当前节点为根节点的完美二叉子树的大小,用一个数组 $\textit{nums}$ 记录所有完美二叉子树的大小。如果以当前节点为根节点的子树不是完美二叉子树,则返回 $-1$。 + +函数 $\textit{dfs}$ 的执行过程如下: + +1. 如果当前节点为空,则返回 $0$; +2. 递归计算左子树和右子树的完美二叉子树的大小,分别记为 $l$ 和 $r$; +3. 如果左子树和右子树的大小不相等,或者左子树和右子树的大小小于 $0$,则返回 $-1$; +4. 计算当前节点的完美二叉子树的大小 $\textit{cnt} = l + r + 1$,并将 $\textit{cnt}$ 添加到数组 $\textit{nums}$ 中; +5. 返回 $\textit{cnt}$。 + +我们调用 $\textit{dfs}$ 函数计算出所有完美二叉子树的大小,如果数组 $\textit{nums}$ 的长度小于 $k$,则返回 $-1$,否则对数组 $\textit{nums}$ 进行降序排序,返回第 $k$ 大的完美二叉子树的大小。 + +时间复杂度 $O(n \times \log n)$,空间复杂度 $O(n)$。其中 $n$ 是二叉树的节点数。 #### Python3 ```python - +# Definition for a binary tree node. +# class TreeNode: +# def __init__(self, val=0, left=None, right=None): +# self.val = val +# self.left = left +# self.right = right +class Solution: + def kthLargestPerfectSubtree(self, root: Optional[TreeNode], k: int) -> int: + def dfs(root: Optional[TreeNode]) -> int: + if root is None: + return 0 + l, r = dfs(root.left), dfs(root.right) + if l < 0 or l != r: + return -1 + cnt = l + r + 1 + nums.append(cnt) + return cnt + + nums = [] + dfs(root) + if len(nums) < k: + return -1 + nums.sort(reverse=True) + return nums[k - 1] ``` #### Java ```java - +/** + * Definition for a binary tree node. + * public class TreeNode { + * int val; + * TreeNode left; + * TreeNode right; + * TreeNode() {} + * TreeNode(int val) { this.val = val; } + * TreeNode(int val, TreeNode left, TreeNode right) { + * this.val = val; + * this.left = left; + * this.right = right; + * } + * } + */ +class Solution { + private Listnums = new ArrayList<>(); + + public int kthLargestPerfectSubtree(TreeNode root, int k) { + dfs(root); + if (nums.size() < k) { + return -1; + } + nums.sort(Comparator.reverseOrder()); + return nums.get(k - 1); + } + + private int dfs(TreeNode root) { + if (root == null) { + return 0; + } + int l = dfs(root.left); + int r = dfs(root.right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.add(cnt); + return cnt; + } +} ``` #### C++ ```cpp - +/** + * Definition for a binary tree node. + * struct TreeNode { + * int val; + * TreeNode *left; + * TreeNode *right; + * TreeNode() : val(0), left(nullptr), right(nullptr) {} + * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} + * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} + * }; + */ +class Solution { +public: + int kthLargestPerfectSubtree(TreeNode* root, int k) { + vector nums; + auto dfs = [&](auto&& dfs, TreeNode* root) -> int { + if (!root) { + return 0; + } + int l = dfs(dfs, root->left); + int r = dfs(dfs, root->right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.push_back(cnt); + return cnt; + }; + dfs(dfs, root); + if (nums.size() < k) { + return -1; + } + ranges::sort(nums, greater ()); + return nums[k - 1]; + } +}; ``` #### Go ```go +/** + * Definition for a binary tree node. + * type TreeNode struct { + * Val int + * Left *TreeNode + * Right *TreeNode + * } + */ +func kthLargestPerfectSubtree(root *TreeNode, k int) int { + nums := []int{} + var dfs func(*TreeNode) int + dfs = func(root *TreeNode) int { + if root == nil { + return 0 + } + l, r := dfs(root.Left), dfs(root.Right) + if l < 0 || l != r { + return -1 + } + cnt := l + r + 1 + nums = append(nums, cnt) + return cnt + } + dfs(root) + if len(nums) < k { + return -1 + } + sort.Sort(sort.Reverse(sort.IntSlice(nums))) + return nums[k-1] +} +``` +#### TypeScript + +```ts +/** + * Definition for a binary tree node. + * class TreeNode { + * val: number + * left: TreeNode | null + * right: TreeNode | null + * constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) { + * this.val = (val===undefined ? 0 : val) + * this.left = (left===undefined ? null : left) + * this.right = (right===undefined ? null : right) + * } + * } + */ + +function kthLargestPerfectSubtree(root: TreeNode | null, k: number): number { + const nums: number[] = []; + const dfs = (root: TreeNode | null): number => { + if (!root) { + return 0; + } + const l = dfs(root.left); + const r = dfs(root.right); + if (l < 0 || l !== r) { + return -1; + } + const cnt = l + r + 1; + nums.push(cnt); + return cnt; + }; + dfs(root); + if (nums.length < k) { + return -1; + } + return nums.sort((a, b) => b - a)[k - 1]; +} ``` diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README_EN.md b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README_EN.md index e13cb8d95decf..b30257addfb7d 100644 --- a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README_EN.md +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/README_EN.md @@ -79,32 +79,213 @@ The 2ndlargest size is 3. -### Solution 1 +### Solution 1: DFS + Sorting + +We define a function $\textit{dfs}$ to calculate the size of the perfect binary subtree rooted at the current node, using an array $\textit{nums}$ to record the sizes of all perfect binary subtrees. If the subtree rooted at the current node is not a perfect binary subtree, it returns $-1$. + +The execution process of the function $\textit{dfs}$ is as follows: + +1. If the current node is null, return $0$; +2. Recursively calculate the sizes of the perfect binary subtrees of the left and right subtrees, denoted as $l$ and $r$ respectively; +3. If the sizes of the left and right subtrees are not equal, or if the sizes of the left and right subtrees are less than $0$, return $-1$; +4. Calculate the size of the perfect binary subtree rooted at the current node $\textit{cnt} = l + r + 1$, and add $\textit{cnt}$ to the array $\textit{nums}$; +5. Return $\textit{cnt}$. + +We call the $\textit{dfs}$ function to calculate the sizes of all perfect binary subtrees. If the length of the array $\textit{nums}$ is less than $k$, return $-1$. Otherwise, sort the array $\textit{nums}$ in descending order and return the $k$-th largest perfect binary subtree size. + +The time complexity is $O(n \times \log n)$, and the space complexity is $O(n)$. Here, $n$ is the number of nodes in the binary tree. #### Python3 ```python - +# Definition for a binary tree node. +# class TreeNode: +# def __init__(self, val=0, left=None, right=None): +# self.val = val +# self.left = left +# self.right = right +class Solution: + def kthLargestPerfectSubtree(self, root: Optional[TreeNode], k: int) -> int: + def dfs(root: Optional[TreeNode]) -> int: + if root is None: + return 0 + l, r = dfs(root.left), dfs(root.right) + if l < 0 or l != r: + return -1 + cnt = l + r + 1 + nums.append(cnt) + return cnt + + nums = [] + dfs(root) + if len(nums) < k: + return -1 + nums.sort(reverse=True) + return nums[k - 1] ``` #### Java ```java - +/** + * Definition for a binary tree node. + * public class TreeNode { + * int val; + * TreeNode left; + * TreeNode right; + * TreeNode() {} + * TreeNode(int val) { this.val = val; } + * TreeNode(int val, TreeNode left, TreeNode right) { + * this.val = val; + * this.left = left; + * this.right = right; + * } + * } + */ +class Solution { + private Listnums = new ArrayList<>(); + + public int kthLargestPerfectSubtree(TreeNode root, int k) { + dfs(root); + if (nums.size() < k) { + return -1; + } + nums.sort(Comparator.reverseOrder()); + return nums.get(k - 1); + } + + private int dfs(TreeNode root) { + if (root == null) { + return 0; + } + int l = dfs(root.left); + int r = dfs(root.right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.add(cnt); + return cnt; + } +} ``` #### C++ ```cpp - +/** + * Definition for a binary tree node. + * struct TreeNode { + * int val; + * TreeNode *left; + * TreeNode *right; + * TreeNode() : val(0), left(nullptr), right(nullptr) {} + * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} + * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} + * }; + */ +class Solution { +public: + int kthLargestPerfectSubtree(TreeNode* root, int k) { + vector nums; + auto dfs = [&](auto&& dfs, TreeNode* root) -> int { + if (!root) { + return 0; + } + int l = dfs(dfs, root->left); + int r = dfs(dfs, root->right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.push_back(cnt); + return cnt; + }; + dfs(dfs, root); + if (nums.size() < k) { + return -1; + } + ranges::sort(nums, greater ()); + return nums[k - 1]; + } +}; ``` #### Go ```go +/** + * Definition for a binary tree node. + * type TreeNode struct { + * Val int + * Left *TreeNode + * Right *TreeNode + * } + */ +func kthLargestPerfectSubtree(root *TreeNode, k int) int { + nums := []int{} + var dfs func(*TreeNode) int + dfs = func(root *TreeNode) int { + if root == nil { + return 0 + } + l, r := dfs(root.Left), dfs(root.Right) + if l < 0 || l != r { + return -1 + } + cnt := l + r + 1 + nums = append(nums, cnt) + return cnt + } + dfs(root) + if len(nums) < k { + return -1 + } + sort.Sort(sort.Reverse(sort.IntSlice(nums))) + return nums[k-1] +} +``` +#### TypeScript + +```ts +/** + * Definition for a binary tree node. + * class TreeNode { + * val: number + * left: TreeNode | null + * right: TreeNode | null + * constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) { + * this.val = (val===undefined ? 0 : val) + * this.left = (left===undefined ? null : left) + * this.right = (right===undefined ? null : right) + * } + * } + */ + +function kthLargestPerfectSubtree(root: TreeNode | null, k: number): number { + const nums: number[] = []; + const dfs = (root: TreeNode | null): number => { + if (!root) { + return 0; + } + const l = dfs(root.left); + const r = dfs(root.right); + if (l < 0 || l !== r) { + return -1; + } + const cnt = l + r + 1; + nums.push(cnt); + return cnt; + }; + dfs(root); + if (nums.length < k) { + return -1; + } + return nums.sort((a, b) => b - a)[k - 1]; +} ``` diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.cpp b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.cpp new file mode 100644 index 0000000000000..b39240437ccb8 --- /dev/null +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.cpp @@ -0,0 +1,36 @@ +/** + * Definition for a binary tree node. + * struct TreeNode { + * int val; + * TreeNode *left; + * TreeNode *right; + * TreeNode() : val(0), left(nullptr), right(nullptr) {} + * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} + * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} + * }; + */ +class Solution { +public: + int kthLargestPerfectSubtree(TreeNode* root, int k) { + vector nums; + auto dfs = [&](auto&& dfs, TreeNode* root) -> int { + if (!root) { + return 0; + } + int l = dfs(dfs, root->left); + int r = dfs(dfs, root->right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.push_back(cnt); + return cnt; + }; + dfs(dfs, root); + if (nums.size() < k) { + return -1; + } + ranges::sort(nums, greater ()); + return nums[k - 1]; + } +}; diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.go b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.go new file mode 100644 index 0000000000000..3fe69a5febb5b --- /dev/null +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.go @@ -0,0 +1,30 @@ +/** + * Definition for a binary tree node. + * type TreeNode struct { + * Val int + * Left *TreeNode + * Right *TreeNode + * } + */ +func kthLargestPerfectSubtree(root *TreeNode, k int) int { + nums := []int{} + var dfs func(*TreeNode) int + dfs = func(root *TreeNode) int { + if root == nil { + return 0 + } + l, r := dfs(root.Left), dfs(root.Right) + if l < 0 || l != r { + return -1 + } + cnt := l + r + 1 + nums = append(nums, cnt) + return cnt + } + dfs(root) + if len(nums) < k { + return -1 + } + sort.Sort(sort.Reverse(sort.IntSlice(nums))) + return nums[k-1] +} diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.java b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.java new file mode 100644 index 0000000000000..cb9558cd8b3bd --- /dev/null +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.java @@ -0,0 +1,41 @@ +/** + * Definition for a binary tree node. + * public class TreeNode { + * int val; + * TreeNode left; + * TreeNode right; + * TreeNode() {} + * TreeNode(int val) { this.val = val; } + * TreeNode(int val, TreeNode left, TreeNode right) { + * this.val = val; + * this.left = left; + * this.right = right; + * } + * } + */ +class Solution { + private List nums = new ArrayList<>(); + + public int kthLargestPerfectSubtree(TreeNode root, int k) { + dfs(root); + if (nums.size() < k) { + return -1; + } + nums.sort(Comparator.reverseOrder()); + return nums.get(k - 1); + } + + private int dfs(TreeNode root) { + if (root == null) { + return 0; + } + int l = dfs(root.left); + int r = dfs(root.right); + if (l < 0 || l != r) { + return -1; + } + int cnt = l + r + 1; + nums.add(cnt); + return cnt; + } +} diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.py b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.py new file mode 100644 index 0000000000000..1bee5e3f37e00 --- /dev/null +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.py @@ -0,0 +1,24 @@ +# Definition for a binary tree node. +# class TreeNode: +# def __init__(self, val=0, left=None, right=None): +# self.val = val +# self.left = left +# self.right = right +class Solution: + def kthLargestPerfectSubtree(self, root: Optional[TreeNode], k: int) -> int: + def dfs(root: Optional[TreeNode]) -> int: + if root is None: + return 0 + l, r = dfs(root.left), dfs(root.right) + if l < 0 or l != r: + return -1 + cnt = l + r + 1 + nums.append(cnt) + return cnt + + nums = [] + dfs(root) + if len(nums) < k: + return -1 + nums.sort(reverse=True) + return nums[k - 1] diff --git a/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.ts b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.ts new file mode 100644 index 0000000000000..c04fc5c5e297d --- /dev/null +++ b/solution/3300-3399/3319.K-th Largest Perfect Subtree Size in Binary Tree/Solution.ts @@ -0,0 +1,35 @@ +/** + * Definition for a binary tree node. + * class TreeNode { + * val: number + * left: TreeNode | null + * right: TreeNode | null + * constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) { + * this.val = (val===undefined ? 0 : val) + * this.left = (left===undefined ? null : left) + * this.right = (right===undefined ? null : right) + * } + * } + */ + +function kthLargestPerfectSubtree(root: TreeNode | null, k: number): number { + const nums: number[] = []; + const dfs = (root: TreeNode | null): number => { + if (!root) { + return 0; + } + const l = dfs(root.left); + const r = dfs(root.right); + if (l < 0 || l !== r) { + return -1; + } + const cnt = l + r + 1; + nums.push(cnt); + return cnt; + }; + dfs(root); + if (nums.length < k) { + return -1; + } + return nums.sort((a, b) => b - a)[k - 1]; +} diff --git a/solution/3300-3399/3322.Premier League Table Ranking III/README.md b/solution/3300-3399/3322.Premier League Table Ranking III/README.md new file mode 100644 index 0000000000000..440984aeb2fa3 --- /dev/null +++ b/solution/3300-3399/3322.Premier League Table Ranking III/README.md @@ -0,0 +1,189 @@ +--- +comments: true +difficulty: 中等 +edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README.md +tags: + - 数据库 +--- + + + +# [3322. 英超积分榜排名 III 🔒](https://leetcode.cn/problems/premier-league-table-ranking-iii) + +[English Version](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README_EN.md) + +## 题目描述 + + + + 表:
+ +SeasonStats++------------------+---------+ +| Column Name | Type | ++------------------+---------+ +| season_id | int | +| team_id | int | +| team_name | varchar | +| matches_played | int | +| wins | int | +| draws | int | +| losses | int | +| goals_for | int | +| goals_against | int | ++------------------+---------+ +(season_id, team_id) 是这张表的唯一主键。 +这张表包含每个赛季中每支球队的赛季 id,队伍 id,队伍名,比赛场次,赢场,平局,输场,进球数 (goals_for),以及失球数 (goals_against)。 ++ +编写一个解决方案来计算 每个赛季每支球队的积分,净胜球 和 排名。排名应确定如下:
+ ++
+ +- 球队首先按总分排名(从高到低)
+- 如果积分持平,球队就会根据净胜球(从最高到最低)进行排名
+- 如果净胜球也持平,则球队将按球队名称按字母顺序排名
+积分如下计算:
+ ++
+ +- 赢局 有
+3点得分- 平局 有
+1点得分- 输局 有
+0点得分净胜球计算如下:
+ +goals_for - goals_against返回结果表以
+ +season_id升序 排序,然后以rank升序 排序,最后以team_name升序 排序。结果格式如下所示。
+ ++ +
示例:
+ +输入:
+ ++ +
SeasonStats表:++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ +| season_id | team_id | team_name | matches_played | wins | draws | losses | goals_for | goals_against | ++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ +| 2021 | 1 | Manchester City | 38 | 29 | 6 | 3 | 99 | 26 | +| 2021 | 2 | Liverpool | 38 | 28 | 8 | 2 | 94 | 26 | +| 2021 | 3 | Chelsea | 38 | 21 | 11 | 6 | 76 | 33 | +| 2021 | 4 | Tottenham | 38 | 22 | 5 | 11 | 69 | 40 | +| 2021 | 5 | Arsenal | 38 | 22 | 3 | 13 | 61 | 48 | +| 2022 | 1 | Manchester City | 38 | 28 | 5 | 5 | 94 | 33 | +| 2022 | 2 | Arsenal | 38 | 26 | 6 | 6 | 88 | 43 | +| 2022 | 3 | Manchester United | 38 | 23 | 6 | 9 | 58 | 43 | +| 2022 | 4 | Newcastle | 38 | 19 | 14 | 5 | 68 | 33 | +| 2022 | 5 | Liverpool | 38 | 19 | 10 | 9 | 75 | 47 | ++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ ++ +输出:
+ +++------------+---------+-------------------+--------+-----------------+------+ +| season_id | team_id | team_name | points | goal_difference | rank | ++------------+---------+-------------------+--------+-----------------+------+ +| 2021 | 1 | Manchester City | 93 | 73 | 1 | +| 2021 | 2 | Liverpool | 92 | 68 | 2 | +| 2021 | 3 | Chelsea | 74 | 43 | 3 | +| 2021 | 4 | Tottenham | 71 | 29 | 4 | +| 2021 | 5 | Arsenal | 69 | 13 | 5 | +| 2022 | 1 | Manchester City | 89 | 61 | 1 | +| 2022 | 2 | Arsenal | 84 | 45 | 2 | +| 2022 | 3 | Manchester United | 75 | 15 | 3 | +| 2022 | 4 | Newcastle | 71 | 35 | 4 | +| 2022 | 5 | Liverpool | 67 | 28 | 5 | ++------------+---------+-------------------+--------+-----------------+------+ ++ +解释:
+ ++
+ + + +## 解法 + + + +### 方法一:窗口函数 + +我们可以使用窗口函数 `RANK()`,将球队按照赛季分组,按照积分、净胜球和球队名称的顺序进行排名。 + +最后,我们只需要按照 `season_id`、`position` 和 `team_name` 进行排序即可。 + + + +#### MySQL + +```sql +SELECT + season_id, + team_id, + team_name, + wins * 3 + draws points, + goals_for - goals_against goal_difference, + RANK() OVER ( + PARTITION BY season_id + ORDER BY wins * 3 + draws DESC, goals_for - goals_against DESC, team_name + ) position +FROM SeasonStats +ORDER BY 1, 6, 3; +``` + +#### Pandas + +```python +import pandas as pd + + +def process_team_standings(season_stats: pd.DataFrame) -> pd.DataFrame: + season_stats["points"] = season_stats["wins"] * 3 + season_stats["draws"] + season_stats["goal_difference"] = ( + season_stats["goals_for"] - season_stats["goals_against"] + ) + + season_stats = season_stats.sort_values( + ["season_id", "points", "goal_difference", "team_name"], + ascending=[True, False, False, True], + ) + + season_stats["position"] = season_stats.groupby("season_id").cumcount() + 1 + + return season_stats[ + ["season_id", "team_id", "team_name", "points", "goal_difference", "position"] + ] +``` + + + + + + diff --git a/solution/3300-3399/3322.Premier League Table Ranking III/README_EN.md b/solution/3300-3399/3322.Premier League Table Ranking III/README_EN.md new file mode 100644 index 0000000000000..cfc805ef73eed --- /dev/null +++ b/solution/3300-3399/3322.Premier League Table Ranking III/README_EN.md @@ -0,0 +1,188 @@ +--- +comments: true +difficulty: Medium +edit_url: https://github.com/doocs/leetcode/edit/main/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README_EN.md +tags: + - Database +--- + + + +# [3322. Premier League Table Ranking III 🔒](https://leetcode.com/problems/premier-league-table-ranking-iii) + +[中文文档](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README.md) + +## Description + + + +- 对于 2021 赛季: +
++
+- 曼城有 93 积分 (29 * 3 + 6 * 1) 以及 73 (99 - 26) 个净胜球。
+- 利物浦有 92 积分 (28 * 3 + 8 * 1) 以及 68 (94 - 26) 个净胜球。
+- 切尔西有 74 积分 (21 * 3 + 11 * 1) 以及 43 (76 - 33) 个净胜球。
+- 托特纳姆有 71 积分 (22 * 3 + 5 * 1) 以及 29 (69 - 40) 个净胜球。
+- 阿森纳有 69 积分 (22 * 3 + 3 * 1) 以及 13 (61 - 48) 个净胜球。
+- 对于 2022 赛季: +
++
+- 曼城有 89 积分 (28 * 3 + 5 * 1) 以及 61 (94 - 33) 个净胜球。
+- 阿森纳有 84 积分 (26 * 3 + 6 * 1) 以及 45 (88 - 43) 个净胜球。
+- 曼联有 75 积分 (23 * 3 + 6 * 1) 以及 15 (58 - 43) 个净胜球。
+- 纽卡斯尔有 71 积分 (19 * 3 + 14 * 1) 以及 35 (68 - 33) 个净胜球。
+- 利物浦有 67 积分 (19 * 3 + 10 * 1) 以及 28 (75 - 47) 个净胜球。
+- 球队首先以积分排名,然后是净胜球,最后是球队名称。
+- 输出以 season_id 升序排序,然后以排名升序排序,最后以 team_name 升序排序。
+Table:
+ +SeasonStats++------------------+---------+ +| Column Name | Type | ++------------------+---------+ +| season_id | int | +| team_id | int | +| team_name | varchar | +| matches_played | int | +| wins | int | +| draws | int | +| losses | int | +| goals_for | int | +| goals_against | int | ++------------------+---------+ +(season_id, team_id) is the unique key for this table. +This table contains season id, team id, team name, matches played, wins, draws, losses, goals scored (goals_for), and goals conceded (goals_against) for each team in each season. ++ +Write a solution to calculate the points, goal difference, and rank for each team in each season. The ranking should be determined as follows:
+ ++
+ +- Teams are first ranked by their total points (highest to lowest)
+- If points are tied, teams are then ranked by their goal difference (highest to lowest)
+- If goal difference is also tied, teams are then ranked alphabetically by team name
+Points are calculated as follows:
+ ++
+ +- +
3points for a win- +
1point for a draw- +
0points for a lossGoal difference is calculated as:
+ +goals_for - goals_againstReturn the result table ordered by
+ +season_idin ascending order, then byrankin ascending order, and finally byteam_namein ascending order.The query result format is in the following example.
+ ++
Example:
+ +Input:
+ ++ +
SeasonStatstable:++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ +| season_id | team_id | team_name | matches_played | wins | draws | losses | goals_for | goals_against | ++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ +| 2021 | 1 | Manchester City | 38 | 29 | 6 | 3 | 99 | 26 | +| 2021 | 2 | Liverpool | 38 | 28 | 8 | 2 | 94 | 26 | +| 2021 | 3 | Chelsea | 38 | 21 | 11 | 6 | 76 | 33 | +| 2021 | 4 | Tottenham | 38 | 22 | 5 | 11 | 69 | 40 | +| 2021 | 5 | Arsenal | 38 | 22 | 3 | 13 | 61 | 48 | +| 2022 | 1 | Manchester City | 38 | 28 | 5 | 5 | 94 | 33 | +| 2022 | 2 | Arsenal | 38 | 26 | 6 | 6 | 88 | 43 | +| 2022 | 3 | Manchester United | 38 | 23 | 6 | 9 | 58 | 43 | +| 2022 | 4 | Newcastle | 38 | 19 | 14 | 5 | 68 | 33 | +| 2022 | 5 | Liverpool | 38 | 19 | 10 | 9 | 75 | 47 | ++------------+---------+-------------------+----------------+------+-------+--------+-----------+---------------+ ++ +Output:
+ +++------------+---------+-------------------+--------+-----------------+------+ +| season_id | team_id | team_name | points | goal_difference | rank | ++------------+---------+-------------------+--------+-----------------+------+ +| 2021 | 1 | Manchester City | 93 | 73 | 1 | +| 2021 | 2 | Liverpool | 92 | 68 | 2 | +| 2021 | 3 | Chelsea | 74 | 43 | 3 | +| 2021 | 4 | Tottenham | 71 | 29 | 4 | +| 2021 | 5 | Arsenal | 69 | 13 | 5 | +| 2022 | 1 | Manchester City | 89 | 61 | 1 | +| 2022 | 2 | Arsenal | 84 | 45 | 2 | +| 2022 | 3 | Manchester United | 75 | 15 | 3 | +| 2022 | 4 | Newcastle | 71 | 35 | 4 | +| 2022 | 5 | Liverpool | 67 | 28 | 5 | ++------------+---------+-------------------+--------+-----------------+------+ ++ +Explanation:
+ ++
+ + + +## Solutions + + + +### Solution 1: Window Function + +We can use the window function `RANK()` to rank the teams by grouping them by season and sorting based on points, goal difference, and team name. + +Finally, we just need to sort by `season_id`, `position`, and `team_name`. + + + +#### MySQL + +```sql +SELECT + season_id, + team_id, + team_name, + wins * 3 + draws points, + goals_for - goals_against goal_difference, + RANK() OVER ( + PARTITION BY season_id + ORDER BY wins * 3 + draws DESC, goals_for - goals_against DESC, team_name + ) position +FROM SeasonStats +ORDER BY 1, 6, 3; +``` + +#### Pandas + +```python +import pandas as pd + + +def process_team_standings(season_stats: pd.DataFrame) -> pd.DataFrame: + season_stats["points"] = season_stats["wins"] * 3 + season_stats["draws"] + season_stats["goal_difference"] = ( + season_stats["goals_for"] - season_stats["goals_against"] + ) + + season_stats = season_stats.sort_values( + ["season_id", "points", "goal_difference", "team_name"], + ascending=[True, False, False, True], + ) + + season_stats["position"] = season_stats.groupby("season_id").cumcount() + 1 + + return season_stats[ + ["season_id", "team_id", "team_name", "points", "goal_difference", "position"] + ] +``` + + + + + + diff --git a/solution/3300-3399/3322.Premier League Table Ranking III/Solution.py b/solution/3300-3399/3322.Premier League Table Ranking III/Solution.py new file mode 100644 index 0000000000000..afbefd8834414 --- /dev/null +++ b/solution/3300-3399/3322.Premier League Table Ranking III/Solution.py @@ -0,0 +1,19 @@ +import pandas as pd + + +def process_team_standings(season_stats: pd.DataFrame) -> pd.DataFrame: + season_stats["points"] = season_stats["wins"] * 3 + season_stats["draws"] + season_stats["goal_difference"] = ( + season_stats["goals_for"] - season_stats["goals_against"] + ) + + season_stats = season_stats.sort_values( + ["season_id", "points", "goal_difference", "team_name"], + ascending=[True, False, False, True], + ) + + season_stats["position"] = season_stats.groupby("season_id").cumcount() + 1 + + return season_stats[ + ["season_id", "team_id", "team_name", "points", "goal_difference", "position"] + ] diff --git a/solution/3300-3399/3322.Premier League Table Ranking III/Solution.sql b/solution/3300-3399/3322.Premier League Table Ranking III/Solution.sql new file mode 100644 index 0000000000000..0b9774594f7d4 --- /dev/null +++ b/solution/3300-3399/3322.Premier League Table Ranking III/Solution.sql @@ -0,0 +1,12 @@ +SELECT + season_id, + team_id, + team_name, + wins * 3 + draws points, + goals_for - goals_against goal_difference, + RANK() OVER ( + PARTITION BY season_id + ORDER BY wins * 3 + draws DESC, goals_for - goals_against DESC, team_name + ) position +FROM SeasonStats +ORDER BY 1, 6, 3; diff --git a/solution/DATABASE_README.md b/solution/DATABASE_README.md index 3a26b58e07d6d..a35d091b26ad7 100644 --- a/solution/DATABASE_README.md +++ b/solution/DATABASE_README.md @@ -297,6 +297,7 @@ | 3278 | [寻找数据科学家职位的候选人 II](/solution/3200-3299/3278.Find%20Candidates%20for%20Data%20Scientist%20Position%20II/README.md) | `数据库` | 中等 | 🔒 | | 3293 | [计算产品最终价格](/solution/3200-3299/3293.Calculate%20Product%20Final%20Price/README.md) | `数据库` | 中等 | 🔒 | | 3308 | [Find Top Performing Driver](/solution/3300-3399/3308.Find%20Top%20Performing%20Driver/README.md) | `数据库` | 中等 | 🔒 | +| 3322 | [英超积分榜排名 III](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README.md) | | 中等 | 🔒 | ## 版权 diff --git a/solution/DATABASE_README_EN.md b/solution/DATABASE_README_EN.md index d1bbd98d8a590..6c3a747cc5d04 100644 --- a/solution/DATABASE_README_EN.md +++ b/solution/DATABASE_README_EN.md @@ -295,6 +295,7 @@ Press Control + F(or Command + F on | 3278 | [Find Candidates for Data Scientist Position II](/solution/3200-3299/3278.Find%20Candidates%20for%20Data%20Scientist%20Position%20II/README_EN.md) | `Database` | Medium | 🔒 | | 3293 | [Calculate Product Final Price](/solution/3200-3299/3293.Calculate%20Product%20Final%20Price/README_EN.md) | `Database` | Medium | 🔒 | | 3308 | [Find Top Performing Driver](/solution/3300-3399/3308.Find%20Top%20Performing%20Driver/README_EN.md) | `Database` | Medium | 🔒 | +| 3322 | [Premier League Table Ranking III](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README_EN.md) | | Medium | 🔒 | ## Copyright diff --git a/solution/README.md b/solution/README.md index 2c7b8baa627b6..2850c846cca7d 100644 --- a/solution/README.md +++ b/solution/README.md @@ -3332,6 +3332,7 @@ | 3319 | [第 K 大的完美二叉子树的大小](/solution/3300-3399/3319.K-th%20Largest%20Perfect%20Subtree%20Size%20in%20Binary%20Tree/README.md) | | 中等 | 第 419 场周赛 | | 3320 | [统计能获胜的出招序列数](/solution/3300-3399/3320.Count%20The%20Number%20of%20Winning%20Sequences/README.md) | | 困难 | 第 419 场周赛 | | 3321 | [计算子数组的 x-sum II](/solution/3300-3399/3321.Find%20X-Sum%20of%20All%20K-Long%20Subarrays%20II/README.md) | | 困难 | 第 419 场周赛 | +| 3322 | [英超积分榜排名 III](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README.md) | | 中等 | 🔒 | ## 版权 diff --git a/solution/README_EN.md b/solution/README_EN.md index f3f8f6d3a7fca..b19bfd7fb70bf 100644 --- a/solution/README_EN.md +++ b/solution/README_EN.md @@ -3330,6 +3330,7 @@ Press Control + F(or Command + F on | 3319 | [K-th Largest Perfect Subtree Size in Binary Tree](/solution/3300-3399/3319.K-th%20Largest%20Perfect%20Subtree%20Size%20in%20Binary%20Tree/README_EN.md) | | Medium | Weekly Contest 419 | | 3320 | [Count The Number of Winning Sequences](/solution/3300-3399/3320.Count%20The%20Number%20of%20Winning%20Sequences/README_EN.md) | | Hard | Weekly Contest 419 | | 3321 | [Find X-Sum of All K-Long Subarrays II](/solution/3300-3399/3321.Find%20X-Sum%20of%20All%20K-Long%20Subarrays%20II/README_EN.md) | | Hard | Weekly Contest 419 | +| 3322 | [Premier League Table Ranking III](/solution/3300-3399/3322.Premier%20League%20Table%20Ranking%20III/README_EN.md) | | Medium | 🔒 | ## Copyright- For the 2021 season: +
++
+- Manchester City has 93 points (29 * 3 + 6 * 1) and a goal difference of 73 (99 - 26).
+- Liverpool has 92 points (28 * 3 + 8 * 1) and a goal difference of 68 (94 - 26).
+- Chelsea has 74 points (21 * 3 + 11 * 1) and a goal difference of 43 (76 - 33).
+- Tottenham has 71 points (22 * 3 + 5 * 1) and a goal difference of 29 (69 - 40).
+- Arsenal has 69 points (22 * 3 + 3 * 1) and a goal difference of 13 (61 - 48).
+- For the 2022 season: +
++
+- Manchester City has 89 points (28 * 3 + 5 * 1) and a goal difference of 61 (94 - 33).
+- Arsenal has 84 points (26 * 3 + 6 * 1) and a goal difference of 45 (88 - 43).
+- Manchester United has 75 points (23 * 3 + 6 * 1) and a goal difference of 15 (58 - 43).
+- Newcastle has 71 points (19 * 3 + 14 * 1) and a goal difference of 35 (68 - 33).
+- Liverpool has 67 points (19 * 3 + 10 * 1) and a goal difference of 28 (75 - 47).
+- The teams are ranked first by points, then by goal difference, and finally by team name.
+- The output is ordered by season_id ascending, then by rank ascending, and finally by team_name ascending.
+