题目:
Given a string s, partition s such that every substring of the partition is a palindrome.
Return the minimum cuts needed for a palindrome partitioning of s.
Example:
Input: "aab" Output: 1 Explanation: The palindrome partitioning ["aa","b"] could be produced using 1 cut.
首先看我的第一种解法:(废了很长时间,做题太少了,动脑太少了),这个运行时间蛮短的
package test;
public class LC132Try3
{
public int minCut(String s)
{
int len = s.length();
int[] dp = new int[len];
char[] arr = s.toCharArray();
//最多需要分j次
for (int j = 0; j < len; j++)
{
dp[j] = j;
}
for (int i = 0; i < len; i++)
{
int m = i - 1;
int n = i + 1;
while (m >= 0 && n < len)
{
if (arr[m] == arr[n])
{
//如果是0则没有必要分割,不需要加1
if (m == 0)
{
dp[n] = Math.min(dp[n], dp[m]);
}
else
{
dp[n] = Math.min(dp[n], dp[m - 1] + 1);
}
m--;
n++;
}
else
{
//如果和他后面的不相同,则更新下后面的,最多就是他前面的加1,防止他就是自己对应自己,自己单独分割
dp[n] = Math.min(dp[n], dp[n-1] + 1);
break;
}
}
m = i;
n = i + 1;
while (m >= 0 && n < len)
{
if (arr[m] == arr[n])
{
if (m == 0)
{
dp[n] = Math.min(dp[n], dp[m]);
}
else
{
dp[n] = Math.min(dp[n], dp[m - 1] + 1);
}
m--;
n++;
}
else
{
dp[n] = Math.min(dp[n], dp[n-1] + 1);
break;
}
}
}
return dp[len - 1];
}
public static void main(String[] args)
{
LC132Try3 t = new LC132Try3();
System.out.println(t.minCut("aaa"));
//System.out.println(t.minCut("eegiicgaeadbcfacfhifdbiehbgejcaeggcgbahfcajfhjjdgj"));
// System.out.println(t.minCut("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabbaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"));
}
}
这种解法就是对应131图的解法,下面是图的另一种解法:这个也蛮烧脑的(just for me),不知道为什么他的运行时间更慢一点(这个就是左程云的回文最少分割数),我只是改成顺序了,但现在觉得还是逆序好。
package test;
public class LC132Try4
{
public int minCut(String s)
{
int len = s.length();
if(s==null || len==0){
return 0;
}
char[] arr= s.toCharArray();
int[] cost=new int[len];
boolean[][] dp=new boolean[len][len];
for(int i=0;i<len;i++){//我这个是顺序,其实逆序更好,就不用判断j==0种情况了。
cost[i]=i;
for(int j=i;j>=0;j--){
if(arr[j]==arr[i]&&( i-j<2 || dp[i-1][j+1] )){
dp[j][i]=true;
if(j==0){
cost[i]=0;
}else{
cost[i]=Math.min(cost[i],cost[j-1]+1);
}
}
}
}
return cost[len-1];
}
public static void main(String[] args)
{
LC132Try4 t = new LC132Try4();
//System.out.println(t.minCut("aaa"));
System.out.println(t.minCut("eegiicgaeadbcfacfhifdbiehbgejcaeggcgbahfcajfhjjdgj"));
// System.out.println(t.minCut("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabbaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"));
}
}
这道题解法到此结束,哈哈,来看下,我的超时解法:
package test;
public class LC132Try2
{
public int minCut(String s)
{
int len=s.length();
int ret=len-1;
if(len==0){
return ret;
}
boolean[][] temp=new boolean[len][len];
setPalindrome(s,temp,len);
ret=getPalindrome(s,temp,len,0);
return ret;
}
public int getPalindrome(String s,boolean[][] temp,int len,int start){
if(start>=len){
return 0;
}
int ret= len-start-1;
for(int i=start;i<len;i++){
if(temp[start][i]){
if(i==len-1){
return 0;
}
int cost=getPalindrome(s,temp,len,i+1);
ret=Math.min(ret, cost+1);
}
}
return ret;
}
public void setPalindrome(String s,boolean[][] temp,int len){
char[] arr= s.toCharArray();
for(int i=0;i<len;i++){
temp[i][i]=true;
int m=i-1;//即以arr[i]为中间的回文;
int n=i+1;
while(m>=0&&n<len){
if(arr[m]==arr[n]){
temp[m][n]=true;
m--;
n++;
}else{
break;
}
}
m=i;//与i对称的回文;
n=i+1;
while(m>=0&&n<len){
if(arr[m]==arr[n]){
temp[m][n]=true;
m--;
n++;
}else{
break;
}
}
}
}
public static void main(String[] args)
{
LC132Try2 t = new LC132Try2();
System.out.println(t.minCut("aba"));
}
}
哈哈
package test;
import java.util.HashMap;
import java.util.Map;
public class LC132Try1
{
public int minCut(String s)
{
Map<String,Integer> map = new HashMap<String,Integer>();
int ret= minCost(s,map);
return ret;
}
public int minCost(String s,Map<String,Integer> map)
{
if(map.containsKey(s)){
return map.get(s);
}
int len = s.length();
int ret = len - 1;
char[] arr=s.toCharArray();
char c=arr[0];
for(int i=0;i<arr.length;i++){
if(arr[i]==c){
String t=s.substring(0, i+1);
if(isPalindrome(t)){
if(i==arr.length-1){
ret= 0;
}else{
int cost=minCost(s.substring(i+1),map);
map.put(s.substring(i+1), cost);
ret=Math.min(ret,cost+1) ;
}
}
}
}
return ret;
}
public boolean isPalindrome(String s){
int len=s.length();
if(len==0){
return false;
}
char[] arr=s.toCharArray();
for(int i=0;i<len/2;i++){
if(arr[i]!=arr[len-i-1]){
return false;
}
}
return true;
}
}