516. 最长回文子序列(leetcode)
https://leetcode.cn/problems/longest-palindromic-subsequence/description/
class Solution {
public int longestPalindromeSubseq(String s) {
// f[i][j]表示s[i:j]中的最长回文子序列的长度
// 以s[i],s[j]是否选择划分子集
// s[i]==s[j],都选,则f[i][j]=f[i+1][j-1]+2;
// s[i]!=s[j],则只能选一边
// 选s[i],f[i][j]=f[i][j-1];
// 选s[j],f[i][j]=f[i+1][j];
// 取max,f[i][j]=max(f[i][j-1],f[i-1][j])
// 而都不选,则f[i+1][j-1],这个子集是最小的,用不到这个情况,只选一边都包含这个子集
// 初始化,f的初值是根基,最开始的最小的集合,即f[i][i]=1,0<i<n
int[][] f=new int[1010][1010];
for(int i=1;i<=s.length();i++)f[i][i]=1;
for(int i=s.length();i>=1;i--)
{
for(int j=i+1;j<=s.length();j++)
{
if(s.charAt(i-1)==s.charAt(j-1)) f[i][j]=f[i+1][j-1]+2;
else f[i][j]=Math.max(f[i+1][j],f[i][j-1]);
}
}
return f[1][s.length()];
}
}
class Solution {
public int longestPalindromeSubseq(String s) {
// 妙法:由于求的是回文子序列,将s倒序后,求s和倒序s的最长公共子序列LCS
// 即是求最长回文子串
int[][] f=new int[1010][1010];
String s2=new StringBuilder(s).reverse().toString();
for(int i=1;i<=s.length();i++)
for(int j=1;j<=s2.length();j++)
{
if(s.charAt(i-1)==s2.charAt(j-1))f[i][j]=f[i-1][j-1]+1;
else f[i][j]=Math.max(f[i-1][j],f[i][j-1]);
}
return f[s.length()][s2.length()];
}
}

浙公网安备 33010602011771号