diff --git a/solution/3600-3699/3642.Find Books with Polarized Opinions/README.md b/solution/3600-3699/3642.Find Books with Polarized Opinions/README.md index 4b947b917ed03..87ca711e1fd48 100644 --- a/solution/3600-3699/3642.Find Books with Polarized Opinions/README.md +++ b/solution/3600-3699/3642.Find Books with Polarized Opinions/README.md @@ -167,14 +167,94 @@ Each row represents a reading session where someone read a portion of a book. se -### 方法一 +### 方法一:连接 + 分组聚合 + +我们可以通过连接 `books` 表和 `reading_sessions` 表,然后对结果进行分组和聚合来实现。 + +首先,我们需要计算每本书的评分范围、极端评分的数量和极端评分的比例。 + +然后,我们可以根据这些指标筛选出符合条件的书籍。 + +最后,按照极端评分比例和书名的降序排列结果。 #### MySQL ```sql +# Write your MySQL query statement below +SELECT + book_id, + title, + author, + genre, + pages, + (MAX(session_rating) - MIN(session_rating)) AS rating_spread, + ROUND((SUM(session_rating <= 2) + SUM(session_rating >= 4)) / COUNT(1), 2) polarization_score +FROM + books + JOIN reading_sessions USING (book_id) +GROUP BY book_id +HAVING + COUNT(1) >= 5 + AND MAX(session_rating) >= 4 + AND MIN(session_rating) <= 2 + AND polarization_score >= 0.6 +ORDER BY polarization_score DESC, title DESC; +``` +#### Pandas + +```python +import pandas as pd +from decimal import Decimal, ROUND_HALF_UP + + +def find_polarized_books( + books: pd.DataFrame, reading_sessions: pd.DataFrame +) -> pd.DataFrame: + df = books.merge(reading_sessions, on="book_id") + agg_df = ( + df.groupby(["book_id", "title", "author", "genre", "pages"]) + .agg( + max_rating=("session_rating", "max"), + min_rating=("session_rating", "min"), + rating_spread=("session_rating", lambda x: x.max() - x.min()), + count_sessions=("session_rating", "count"), + low_or_high_count=("session_rating", lambda x: ((x <= 2) | (x >= 4)).sum()), + ) + .reset_index() + ) + + agg_df["polarization_score"] = agg_df.apply( + lambda r: float( + Decimal(r["low_or_high_count"] / r["count_sessions"]).quantize( + Decimal("0.01"), rounding=ROUND_HALF_UP + ) + ), + axis=1, + ) + + result = agg_df[ + (agg_df["count_sessions"] >= 5) + & (agg_df["max_rating"] >= 4) + & (agg_df["min_rating"] <= 2) + & (agg_df["polarization_score"] >= 0.6) + ] + + return result.sort_values( + by=["polarization_score", "title"], ascending=[False, False] + )[ + [ + "book_id", + "title", + "author", + "genre", + "pages", + "rating_spread", + "polarization_score", + ] + ] ``` diff --git a/solution/3600-3699/3642.Find Books with Polarized Opinions/README_EN.md b/solution/3600-3699/3642.Find Books with Polarized Opinions/README_EN.md index 0726ab18c2fbd..bcb28b7ad8b7b 100644 --- a/solution/3600-3699/3642.Find Books with Polarized Opinions/README_EN.md +++ b/solution/3600-3699/3642.Find Books with Polarized Opinions/README_EN.md @@ -167,14 +167,94 @@ Each row represents a reading session where someone read a portion of a book. se -### Solution 1 +### Solution 1: Join + Group Aggregation + +We can implement this by joining the `books` table with the `reading_sessions` table, then grouping and aggregating the results. + +First, we need to calculate the rating range, the number of extreme ratings, and the proportion of extreme ratings for each book. + +Then, we can filter out books that meet the criteria based on these metrics. + +Finally, sort the results by extreme rating proportion and book title in descending order. #### MySQL ```sql +# Write your MySQL query statement below +SELECT + book_id, + title, + author, + genre, + pages, + (MAX(session_rating) - MIN(session_rating)) AS rating_spread, + ROUND((SUM(session_rating <= 2) + SUM(session_rating >= 4)) / COUNT(1), 2) polarization_score +FROM + books + JOIN reading_sessions USING (book_id) +GROUP BY book_id +HAVING + COUNT(1) >= 5 + AND MAX(session_rating) >= 4 + AND MIN(session_rating) <= 2 + AND polarization_score >= 0.6 +ORDER BY polarization_score DESC, title DESC; +``` +#### Pandas + +```python +import pandas as pd +from decimal import Decimal, ROUND_HALF_UP + + +def find_polarized_books( + books: pd.DataFrame, reading_sessions: pd.DataFrame +) -> pd.DataFrame: + df = books.merge(reading_sessions, on="book_id") + agg_df = ( + df.groupby(["book_id", "title", "author", "genre", "pages"]) + .agg( + max_rating=("session_rating", "max"), + min_rating=("session_rating", "min"), + rating_spread=("session_rating", lambda x: x.max() - x.min()), + count_sessions=("session_rating", "count"), + low_or_high_count=("session_rating", lambda x: ((x <= 2) | (x >= 4)).sum()), + ) + .reset_index() + ) + + agg_df["polarization_score"] = agg_df.apply( + lambda r: float( + Decimal(r["low_or_high_count"] / r["count_sessions"]).quantize( + Decimal("0.01"), rounding=ROUND_HALF_UP + ) + ), + axis=1, + ) + + result = agg_df[ + (agg_df["count_sessions"] >= 5) + & (agg_df["max_rating"] >= 4) + & (agg_df["min_rating"] <= 2) + & (agg_df["polarization_score"] >= 0.6) + ] + + return result.sort_values( + by=["polarization_score", "title"], ascending=[False, False] + )[ + [ + "book_id", + "title", + "author", + "genre", + "pages", + "rating_spread", + "polarization_score", + ] + ] ``` diff --git a/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.py b/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.py new file mode 100644 index 0000000000000..a1f5191e29716 --- /dev/null +++ b/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.py @@ -0,0 +1,49 @@ +import pandas as pd +from decimal import Decimal, ROUND_HALF_UP + + +def find_polarized_books( + books: pd.DataFrame, reading_sessions: pd.DataFrame +) -> pd.DataFrame: + df = books.merge(reading_sessions, on="book_id") + agg_df = ( + df.groupby(["book_id", "title", "author", "genre", "pages"]) + .agg( + max_rating=("session_rating", "max"), + min_rating=("session_rating", "min"), + rating_spread=("session_rating", lambda x: x.max() - x.min()), + count_sessions=("session_rating", "count"), + low_or_high_count=("session_rating", lambda x: ((x <= 2) | (x >= 4)).sum()), + ) + .reset_index() + ) + + agg_df["polarization_score"] = agg_df.apply( + lambda r: float( + Decimal(r["low_or_high_count"] / r["count_sessions"]).quantize( + Decimal("0.01"), rounding=ROUND_HALF_UP + ) + ), + axis=1, + ) + + result = agg_df[ + (agg_df["count_sessions"] >= 5) + & (agg_df["max_rating"] >= 4) + & (agg_df["min_rating"] <= 2) + & (agg_df["polarization_score"] >= 0.6) + ] + + return result.sort_values( + by=["polarization_score", "title"], ascending=[False, False] + )[ + [ + "book_id", + "title", + "author", + "genre", + "pages", + "rating_spread", + "polarization_score", + ] + ] diff --git a/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.sql b/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.sql new file mode 100644 index 0000000000000..badc821ce8351 --- /dev/null +++ b/solution/3600-3699/3642.Find Books with Polarized Opinions/Solution.sql @@ -0,0 +1,19 @@ +# Write your MySQL query statement below +SELECT + book_id, + title, + author, + genre, + pages, + (MAX(session_rating) - MIN(session_rating)) AS rating_spread, + ROUND((SUM(session_rating <= 2) + SUM(session_rating >= 4)) / COUNT(1), 2) polarization_score +FROM + books + JOIN reading_sessions USING (book_id) +GROUP BY book_id +HAVING + COUNT(1) >= 5 + AND MAX(session_rating) >= 4 + AND MIN(session_rating) <= 2 + AND polarization_score >= 0.6 +ORDER BY polarization_score DESC, title DESC; diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/README.md b/solution/3600-3699/3643.Flip Square Submatrix Vertically/README.md index 18325b4729b28..ab9865b775ac9 100644 --- a/solution/3600-3699/3643.Flip Square Submatrix Vertically/README.md +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/README.md @@ -68,32 +68,95 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3600-3699/3643.Fl -### 方法一 +### 方法一:模拟 + +我们从第 $x$ 行开始,一共翻转 $\lfloor \frac{k}{2} \rfloor$ 行。 + +对于每一行 $i$,我们需要将其与对应的行 $i_2$ 进行交换,其中 $i_2 = x + k - 1 - (i - x)$。 + +在交换时,我们需要遍历 $j \in [y, y + k)$,将 $\text{grid}[i][j]$ 和 $\text{grid}[i_2][j]$ 进行交换。 + +最后,返回更新后的矩阵。 + +时间复杂度 $O(k^2)$,其中 $k$ 是子矩阵的边长。空间复杂度 $O(1)$。 #### Python3 ```python - +class Solution: + def reverseSubmatrix( + self, grid: List[List[int]], x: int, y: int, k: int + ) -> List[List[int]]: + for i in range(x, x + k // 2): + i2 = x + k - 1 - (i - x) + for j in range(y, y + k): + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + return grid ``` #### Java ```java - +class Solution { + public int[][] reverseSubmatrix(int[][] grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + int t = grid[i][j]; + grid[i][j] = grid[i2][j]; + grid[i2][j] = t; + } + } + return grid; + } +} ``` #### C++ ```cpp - +class Solution { +public: + vector> reverseSubmatrix(vector>& grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + swap(grid[i][j], grid[i2][j]); + } + } + return grid; + } +}; ``` #### Go ```go +func reverseSubmatrix(grid [][]int, x int, y int, k int) [][]int { + for i := x; i < x+k/2; i++ { + i2 := x + k - 1 - (i - x) + for j := y; j < y+k; j++ { + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + } + } + return grid +} +``` +#### TypeScript + +```ts +function reverseSubmatrix(grid: number[][], x: number, y: number, k: number): number[][] { + for (let i = x; i < x + Math.floor(k / 2); i++) { + const i2 = x + k - 1 - (i - x); + for (let j = y; j < y + k; j++) { + [grid[i][j], grid[i2][j]] = [grid[i2][j], grid[i][j]]; + } + } + return grid; +} ``` diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/README_EN.md b/solution/3600-3699/3643.Flip Square Submatrix Vertically/README_EN.md index 0c5d31c2af462..4122d15856154 100644 --- a/solution/3600-3699/3643.Flip Square Submatrix Vertically/README_EN.md +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/README_EN.md @@ -66,32 +66,95 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3600-3699/3643.Fl -### Solution 1 +### Solution 1: Simulation + +We start from row $x$ and flip a total of $\lfloor \frac{k}{2} \rfloor$ rows. + +For each row $i$, we need to swap it with the corresponding row $i_2$, where $i_2 = x + k - 1 - (i - x)$. + +During the swap, we need to traverse $j \in [y, y + k)$ and swap $\text{grid}[i][j]$ with $\text{grid}[i_2][j]$. + +Finally, return the updated matrix. + +The time complexity is $O(k^2)$, where $k$ is the side length of the submatrix. The space complexity is $O(1)$. #### Python3 ```python - +class Solution: + def reverseSubmatrix( + self, grid: List[List[int]], x: int, y: int, k: int + ) -> List[List[int]]: + for i in range(x, x + k // 2): + i2 = x + k - 1 - (i - x) + for j in range(y, y + k): + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + return grid ``` #### Java ```java - +class Solution { + public int[][] reverseSubmatrix(int[][] grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + int t = grid[i][j]; + grid[i][j] = grid[i2][j]; + grid[i2][j] = t; + } + } + return grid; + } +} ``` #### C++ ```cpp - +class Solution { +public: + vector> reverseSubmatrix(vector>& grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + swap(grid[i][j], grid[i2][j]); + } + } + return grid; + } +}; ``` #### Go ```go +func reverseSubmatrix(grid [][]int, x int, y int, k int) [][]int { + for i := x; i < x+k/2; i++ { + i2 := x + k - 1 - (i - x) + for j := y; j < y+k; j++ { + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + } + } + return grid +} +``` +#### TypeScript + +```ts +function reverseSubmatrix(grid: number[][], x: number, y: number, k: number): number[][] { + for (let i = x; i < x + Math.floor(k / 2); i++) { + const i2 = x + k - 1 - (i - x); + for (let j = y; j < y + k; j++) { + [grid[i][j], grid[i2][j]] = [grid[i2][j], grid[i][j]]; + } + } + return grid; +} ``` diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.cpp b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.cpp new file mode 100644 index 0000000000000..6db199c122e6c --- /dev/null +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.cpp @@ -0,0 +1,12 @@ +class Solution { +public: + vector> reverseSubmatrix(vector>& grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + swap(grid[i][j], grid[i2][j]); + } + } + return grid; + } +}; diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.go b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.go new file mode 100644 index 0000000000000..da30170fd67f4 --- /dev/null +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.go @@ -0,0 +1,9 @@ +func reverseSubmatrix(grid [][]int, x int, y int, k int) [][]int { + for i := x; i < x+k/2; i++ { + i2 := x + k - 1 - (i - x) + for j := y; j < y+k; j++ { + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + } + } + return grid +} diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.java b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.java new file mode 100644 index 0000000000000..83adf4db4a10a --- /dev/null +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.java @@ -0,0 +1,13 @@ +class Solution { + public int[][] reverseSubmatrix(int[][] grid, int x, int y, int k) { + for (int i = x; i < x + k / 2; i++) { + int i2 = x + k - 1 - (i - x); + for (int j = y; j < y + k; j++) { + int t = grid[i][j]; + grid[i][j] = grid[i2][j]; + grid[i2][j] = t; + } + } + return grid; + } +} diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.py b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.py new file mode 100644 index 0000000000000..97e90d546e3a7 --- /dev/null +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.py @@ -0,0 +1,9 @@ +class Solution: + def reverseSubmatrix( + self, grid: List[List[int]], x: int, y: int, k: int + ) -> List[List[int]]: + for i in range(x, x + k // 2): + i2 = x + k - 1 - (i - x) + for j in range(y, y + k): + grid[i][j], grid[i2][j] = grid[i2][j], grid[i][j] + return grid diff --git a/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.ts b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.ts new file mode 100644 index 0000000000000..d995444a78585 --- /dev/null +++ b/solution/3600-3699/3643.Flip Square Submatrix Vertically/Solution.ts @@ -0,0 +1,9 @@ +function reverseSubmatrix(grid: number[][], x: number, y: number, k: number): number[][] { + for (let i = x; i < x + Math.floor(k / 2); i++) { + const i2 = x + k - 1 - (i - x); + for (let j = y; j < y + k; j++) { + [grid[i][j], grid[i2][j]] = [grid[i2][j], grid[i][j]]; + } + } + return grid; +}