Skip to content

Commit 243d846

Browse files
committed
feat: add solutions to lc problem: No.1771
No.1771.Maximize Palindrome Length From Subsequences
1 parent 54b5eab commit 243d846

File tree

6 files changed

+314
-2
lines changed

6 files changed

+314
-2
lines changed

solution/1700-1799/1771.Maximize Palindrome Length From Subsequences/README.md

Lines changed: 117 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,22 +53,138 @@
5353

5454
<!-- 这里可写通用的实现逻辑 -->
5555

56+
**方法一:动态规划**
57+
58+
我们首先将字符串 `word1``word2` 连接起来,得到字符串 $s$,然后我们可以将问题转化为求字符串 $s$ 的最长回文子序列的长度。只不过这里在算最后的答案时,需要保证回文字符串中,至少有一个字符来自 `word1`,另一个字符来自 `word2`
59+
60+
我们定义 $f[i][j]$ 表示字符串 $s$ 中下标范围在 $[i, j]$ 内的子串的最长回文子序列的长度。
61+
62+
如果 $s[i] = s[j]$,那么 $s[i]$ 和 $s[j]$ 一定在最长回文子序列中,此时 $f[i][j] = f[i + 1][j - 1] + 2$,这时候我们还需要判断 $s[i]$ 和 $s[j]$ 是否来自 `word1``word2`,如果是,我们将答案的最大值更新为 $ans=\max(ans, f[i][j])$。
63+
64+
如果 $s[i] \neq s[j]$,那么 $s[i]$ 和 $s[j]$ 一定不会同时出现在最长回文子序列中,此时 $f[i][j] = max(f[i + 1][j], f[i][j - 1])$。
65+
66+
最后我们返回答案即可。
67+
68+
时间复杂度为 $O(n^2)$,其中 $n$ 是字符串 $s$ 的长度。
69+
5670
<!-- tabs:start -->
5771

5872
### **Python3**
5973

6074
<!-- 这里可写当前语言的特殊实现逻辑 -->
6175

6276
```python
63-
77+
class Solution:
78+
def longestPalindrome(self, word1: str, word2: str) -> int:
79+
s = word1 + word2
80+
n = len(s)
81+
f = [[0] * n for _ in range(n)]
82+
for i in range(n):
83+
f[i][i] = 1
84+
ans = 0
85+
for i in range(n - 1, -1, -1):
86+
for j in range(i + 1, n):
87+
if s[i] == s[j]:
88+
f[i][j] = f[i + 1][j - 1] + 2
89+
if i < len(word1) and j >= len(word1):
90+
ans = max(ans, f[i][j])
91+
else:
92+
f[i][j] = max(f[i + 1][j], f[i][j - 1])
93+
return ans
6494
```
6595

6696
### **Java**
6797

6898
<!-- 这里可写当前语言的特殊实现逻辑 -->
6999

70100
```java
101+
class Solution {
102+
public int longestPalindrome(String word1, String word2) {
103+
String s = word1 + word2;
104+
int n = s.length();
105+
int[][] f = new int[n][n];
106+
for (int i = 0; i < n; ++i) {
107+
f[i][i] = 1;
108+
}
109+
int ans = 0;
110+
for (int i = n - 2; i >= 0; --i) {
111+
for (int j = i + 1; j < n; ++j) {
112+
if (s.charAt(i) == s.charAt(j)) {
113+
f[i][j] = f[i + 1][j - 1] + 2;
114+
if (i < word1.length() && j >= word1.length()) {
115+
ans = Math.max(ans, f[i][j]);
116+
}
117+
} else {
118+
f[i][j] = Math.max(f[i + 1][j], f[i][j - 1]);
119+
}
120+
}
121+
}
122+
return ans;
123+
}
124+
}
125+
```
126+
127+
### **C++**
128+
129+
```cpp
130+
class Solution {
131+
public:
132+
int longestPalindrome(string word1, string word2) {
133+
string s = word1 + word2;
134+
int n = s.size();
135+
int f[n][n];
136+
memset(f, 0, sizeof f);
137+
for (int i = 0; i < n; ++i) f[i][i] = 1;
138+
int ans = 0;
139+
for (int i = n - 2; ~i; --i) {
140+
for (int j = i + 1; j < n; ++j) {
141+
if (s[i] == s[j]) {
142+
f[i][j] = f[i + 1][j - 1] + 2;
143+
if (i < word1.size() && j >= word1.size()) {
144+
ans = max(ans, f[i][j]);
145+
}
146+
} else {
147+
f[i][j] = max(f[i + 1][j], f[i][j - 1]);
148+
}
149+
}
150+
}
151+
return ans;
152+
}
153+
};
154+
```
71155
156+
### **Go**
157+
158+
```go
159+
func longestPalindrome(word1 string, word2 string) (ans int) {
160+
s := word1 + word2
161+
n := len(s)
162+
f := make([][]int, n)
163+
for i := range f {
164+
f[i] = make([]int, n)
165+
f[i][i] = 1
166+
}
167+
for i := n - 2; i >= 0; i-- {
168+
for j := i + 1; j < n; j++ {
169+
if s[i] == s[j] {
170+
f[i][j] = f[i+1][j-1] + 2
171+
if i < len(word1) && j >= len(word1) && ans < f[i][j] {
172+
ans = f[i][j]
173+
}
174+
} else {
175+
f[i][j] = max(f[i+1][j], f[i][j-1])
176+
}
177+
}
178+
}
179+
return ans
180+
}
181+
182+
func max(a, b int) int {
183+
if a > b {
184+
return a
185+
}
186+
return b
187+
}
72188
```
73189

74190
### **...**

solution/1700-1799/1771.Maximize Palindrome Length From Subsequences/README_EN.md

Lines changed: 103 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,13 +55,115 @@
5555
### **Python3**
5656

5757
```python
58-
58+
class Solution:
59+
def longestPalindrome(self, word1: str, word2: str) -> int:
60+
s = word1 + word2
61+
n = len(s)
62+
f = [[0] * n for _ in range(n)]
63+
for i in range(n):
64+
f[i][i] = 1
65+
ans = 0
66+
for i in range(n - 1, -1, -1):
67+
for j in range(i + 1, n):
68+
if s[i] == s[j]:
69+
f[i][j] = f[i + 1][j - 1] + 2
70+
if i < len(word1) and j >= len(word1):
71+
ans = max(ans, f[i][j])
72+
else:
73+
f[i][j] = max(f[i + 1][j], f[i][j - 1])
74+
return ans
5975
```
6076

6177
### **Java**
6278

6379
```java
80+
class Solution {
81+
public int longestPalindrome(String word1, String word2) {
82+
String s = word1 + word2;
83+
int n = s.length();
84+
int[][] f = new int[n][n];
85+
for (int i = 0; i < n; ++i) {
86+
f[i][i] = 1;
87+
}
88+
int ans = 0;
89+
for (int i = n - 2; i >= 0; --i) {
90+
for (int j = i + 1; j < n; ++j) {
91+
if (s.charAt(i) == s.charAt(j)) {
92+
f[i][j] = f[i + 1][j - 1] + 2;
93+
if (i < word1.length() && j >= word1.length()) {
94+
ans = Math.max(ans, f[i][j]);
95+
}
96+
} else {
97+
f[i][j] = Math.max(f[i + 1][j], f[i][j - 1]);
98+
}
99+
}
100+
}
101+
return ans;
102+
}
103+
}
104+
```
105+
106+
### **C++**
107+
108+
```cpp
109+
class Solution {
110+
public:
111+
int longestPalindrome(string word1, string word2) {
112+
string s = word1 + word2;
113+
int n = s.size();
114+
int f[n][n];
115+
memset(f, 0, sizeof f);
116+
for (int i = 0; i < n; ++i) f[i][i] = 1;
117+
int ans = 0;
118+
for (int i = n - 2; ~i; --i) {
119+
for (int j = i + 1; j < n; ++j) {
120+
if (s[i] == s[j]) {
121+
f[i][j] = f[i + 1][j - 1] + 2;
122+
if (i < word1.size() && j >= word1.size()) {
123+
ans = max(ans, f[i][j]);
124+
}
125+
} else {
126+
f[i][j] = max(f[i + 1][j], f[i][j - 1]);
127+
}
128+
}
129+
}
130+
return ans;
131+
}
132+
};
133+
```
64134
135+
### **Go**
136+
137+
```go
138+
func longestPalindrome(word1 string, word2 string) (ans int) {
139+
s := word1 + word2
140+
n := len(s)
141+
f := make([][]int, n)
142+
for i := range f {
143+
f[i] = make([]int, n)
144+
f[i][i] = 1
145+
}
146+
for i := n - 2; i >= 0; i-- {
147+
for j := i + 1; j < n; j++ {
148+
if s[i] == s[j] {
149+
f[i][j] = f[i+1][j-1] + 2
150+
if i < len(word1) && j >= len(word1) && ans < f[i][j] {
151+
ans = f[i][j]
152+
}
153+
} else {
154+
f[i][j] = max(f[i+1][j], f[i][j-1])
155+
}
156+
}
157+
}
158+
return ans
159+
}
160+
161+
func max(a, b int) int {
162+
if a > b {
163+
return a
164+
}
165+
return b
166+
}
65167
```
66168

67169
### **...**
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
class Solution {
2+
public:
3+
int longestPalindrome(string word1, string word2) {
4+
string s = word1 + word2;
5+
int n = s.size();
6+
int f[n][n];
7+
memset(f, 0, sizeof f);
8+
for (int i = 0; i < n; ++i) f[i][i] = 1;
9+
int ans = 0;
10+
for (int i = n - 2; ~i; --i) {
11+
for (int j = i + 1; j < n; ++j) {
12+
if (s[i] == s[j]) {
13+
f[i][j] = f[i + 1][j - 1] + 2;
14+
if (i < word1.size() && j >= word1.size()) {
15+
ans = max(ans, f[i][j]);
16+
}
17+
} else {
18+
f[i][j] = max(f[i + 1][j], f[i][j - 1]);
19+
}
20+
}
21+
}
22+
return ans;
23+
}
24+
};
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
func longestPalindrome(word1 string, word2 string) (ans int) {
2+
s := word1 + word2
3+
n := len(s)
4+
f := make([][]int, n)
5+
for i := range f {
6+
f[i] = make([]int, n)
7+
f[i][i] = 1
8+
}
9+
for i := n - 2; i >= 0; i-- {
10+
for j := i + 1; j < n; j++ {
11+
if s[i] == s[j] {
12+
f[i][j] = f[i+1][j-1] + 2
13+
if i < len(word1) && j >= len(word1) && ans < f[i][j] {
14+
ans = f[i][j]
15+
}
16+
} else {
17+
f[i][j] = max(f[i+1][j], f[i][j-1])
18+
}
19+
}
20+
}
21+
return ans
22+
}
23+
24+
func max(a, b int) int {
25+
if a > b {
26+
return a
27+
}
28+
return b
29+
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
class Solution {
2+
public int longestPalindrome(String word1, String word2) {
3+
String s = word1 + word2;
4+
int n = s.length();
5+
int[][] f = new int[n][n];
6+
for (int i = 0; i < n; ++i) {
7+
f[i][i] = 1;
8+
}
9+
int ans = 0;
10+
for (int i = n - 2; i >= 0; --i) {
11+
for (int j = i + 1; j < n; ++j) {
12+
if (s.charAt(i) == s.charAt(j)) {
13+
f[i][j] = f[i + 1][j - 1] + 2;
14+
if (i < word1.length() && j >= word1.length()) {
15+
ans = Math.max(ans, f[i][j]);
16+
}
17+
} else {
18+
f[i][j] = Math.max(f[i + 1][j], f[i][j - 1]);
19+
}
20+
}
21+
}
22+
return ans;
23+
}
24+
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
class Solution:
2+
def longestPalindrome(self, word1: str, word2: str) -> int:
3+
s = word1 + word2
4+
n = len(s)
5+
f = [[0] * n for _ in range(n)]
6+
for i in range(n):
7+
f[i][i] = 1
8+
ans = 0
9+
for i in range(n - 1, -1, -1):
10+
for j in range(i + 1, n):
11+
if s[i] == s[j]:
12+
f[i][j] = f[i + 1][j - 1] + 2
13+
if i < len(word1) and j >= len(word1):
14+
ans = max(ans, f[i][j])
15+
else:
16+
f[i][j] = max(f[i + 1][j], f[i][j - 1])
17+
return ans

0 commit comments

Comments
 (0)