C++24小時制轉換成12小時制
阿新 • • 發佈:2020-12-13
最長迴文子序列
題目:給定一個字串s,找到其中最長的迴文子序列(注意,子序列跟子串是不一樣的。子序列是從字串中取出元素,相對順序不變,但是可以不挨著。子串肯定是擷取一段)
解法
- 遞迴
- 自頂向下的備忘錄
- 自底向上的動態規劃
- 狀態定義:dp[i][j]表示s的第i個字元到第j個字元之間組成的子序列中,最長的迴文子序列的長度是多少?
- 狀態轉移方程:(然後注意遍歷順序,i 從最後一個字元開始往前遍歷,j 從 i + 1 開始往後遍歷,這樣可以保證每個子問題都已經算好了)
---> dp[i][j] = dp[i+1][j-1] +2; if s[i] == s[j]
---> dp[i][j] = max{dp[i+1][j] , dp[i][j-1]} ,else if s[i] != s[j]
- 初始化:dp[i][i] == 1
- 結果:dp[0][n-1]
動態規劃求解的過程
All Coding
import java.util.*; class Solution{ /** 給定一個字串s,找到其中最長的迴文子序列 注意,子序列跟子串是不一樣的。子序列是從字串中取出元素,相對順序不變,但是可以不挨著。子串肯定是擷取一段。 */ public static void main(String[] args) { String s = "bbbab"; System.out.println("-------------------"); System.out.println(lps1(s)); System.out.println("-------------------"); System.out.println(lps2(s)); System.out.println("-------------------"); System.out.println(lps3(s)); } /** 遞迴 */ public static int lps1(String s){ if(s == null || s.length() == 0) return 0; int len = s.length(); char[] str = s.toCharArray(); return helper1(str,0,len-1); } public static int helper1(char[] str,int i,int j){ if(i==j) return 1; if(i==j-1) return str[i] == str[j]?2:1; if(str[i] == str[j]) return 2 + helper1(str,i+1,j-1); else return Math.max(helper1(str,i,j-1),helper1(str,i+1,j)); } /** 備忘錄 */ public static int lps2(String s){ if(s == null || s.length() == 0) return 0; int len = s.length(); char[] str = s.toCharArray(); int[][] re = new int[len][len]; return helper2(str,0,len-1,re); } public static int helper2(char[] str,int i,int j,int[][] re){ if(re[i][j]!=0) return re[i][j]; if(i==j) return re[i][j] = 1; if(i==j-1) return re[i][j] = str[i] == str[j]?2:1; if(str[i] == str[j]) return re[i][j] = 2 + helper1(str,i+1,j-1); else return re[i][j] = Math.max(helper1(str,i,j-1),helper1(str,i+1,j)); } /** dp,也就是自底向上 狀態定義:dp[i][j]表示s的第i個字元到第j個字元之間組成的子序列中,最長的迴文子序列的長度是多少? 狀態轉移方程:(然後注意遍歷順序,i 從最後一個字元開始往前遍歷,j 從 i + 1 開始往後遍歷,這樣可以保證每個子問題都已經算好了。) dp[i][j] = dp[i+1][j-1] +2; if s[i] == s[j] dp[i][j] = max{dp[i+1][j] , dp[i][j-1]} ,else if s[i] != s[j] 初始化:dp[i][i] == 1 結果:dp[0][n-1] */ public static int lps3(String s){ if(s==null || s.length() == 0) return 0; int len = s.length(); char[] str = s.toCharArray(); int[][] dp = new int[len][len]; for(int i = len-1;i>=0;i--){ dp[i][i] = 1; for(int j = i+1;j<len;j++){ if(str[i] == str[j]) dp[i][j] = dp[i+1][j-1] +2; else dp[i][j] = Math.max(dp[i+1][j],dp[i][j-1]); } } return dp[0][len-1]; } }