Leetcode 题解 - 搜索--Backtracking(21):分割字符串使得每个部分都是回文数

[LeetCode] Palindrome Partitioning 拆分回文串

 

Given a string s, partition s such that every substring of the partition is a palindrome.

Return all possible palindrome partitioning of s.

Example:

Input: "aab"
Output:
[
  ["aa","b"],
  ["a","a","b"]
]

 

这又是一道需要用DFS来解的题目,既然题目要求找到所有可能拆分成回文数的情况,那么肯定是所有的情况都要遍历到,对于每一个子字符串都要分别判断一次是不是回文数,那么肯定有一个判断回文数的子函数,还需要一个DFS函数用来递归,再加上原本的这个函数,总共需要三个函数来求解。我们将已经检测好的回文子串放到字符串数组out中,当s遍历完了之后,将out加入结果res中。那么在递归函数中我们必须要知道当前遍历到的位置,用变量start来表示,所以在递归函数中,如果start等于字符串s的长度,说明已经遍历完成,将out加入结果res中,并返回。否则就从start处开始遍历,由于不知道该如何切割,所以我们要遍历所有的切割情况,即一个字符,两个字符,三个字符,等等。。首先判断取出的子串是否是回文串,调用一个判定回文串的子函数即可,这个子函数传入了子串的起始和终止的范围,若子串是回文串,那么我们将其加入out,并且调用递归函数,此时start传入 i+1,之后还要恢复out的状态。

那么,对原字符串的所有子字符串的访问顺序是什么呢,如果原字符串是 abcd, 那么访问顺序为: a -> b -> c -> d -> cd -> bc -> bcd-> ab -> abc -> abcd, 这是对于没有两个或两个以上子回文串的情况。那么假如原字符串是 aabc,那么访问顺序为:a -> a -> b -> c -> bc -> ab -> abc -> aa -> b -> c -> bc -> aab -> aabc,中间当检测到aa时候,发现是回文串,那么对于剩下的bc当做一个新串来检测,于是有 b -> c -> bc,这样扫描了所有情况,即可得出最终答案,代码如下:

主要看递归的for循环,第一层for是指我String回文第一个有几个字符 1, 2 ,3 ,4 ,5 都有可能

取完第一个回文后,剩下的字串取回文还有 1 , 2, 3 ,4 5, 等可能,接着来 一层一层的取回文,直到把String分割完了,就加到List里面,这里if用的细节,报这个了我们每次分割的都是回文,不是的话就没必要浪费这个实干;

 

class Solution {
    public List<List<String>> partition(String s) {
    List<List<String>> partitions = new ArrayList<>();
    List<String> tempPartition = new ArrayList<>();
    doPartition(s, partitions, tempPartition);
    return partitions;
}

    private void doPartition(String s, List<List<String>> partitions, 
                             List<String> tempPartition) {
        if (s.length() == 0) {
            partitions.add(new ArrayList<>(tempPartition));
            return;
        }
        for (int i = 0; i < s.length(); i++) {
            if (isPalindrome(s, 0, i)) {
                //取到的是0-i的String
                tempPartition.add(s.substring(0, i + 1));
                doPartition(s.substring(i + 1), partitions, tempPartition);
                tempPartition.remove(tempPartition.size() - 1);
            }
        }
    }

    private boolean isPalindrome(String s, int begin, int end) {
        while (begin < end) {
            if (s.charAt(begin++) != s.charAt(end--)) {
                return false;
            }
        }
        return true;
    }
}

 

class Solution {
    public List<List<String>> partition(String s) {
        List<String> list = new ArrayList<>();
        List<List<String>> result = new ArrayList<>();
        help(list, result, s);
        return result;
    }
    
    private void help(List<String> list, List<List<String>> result, String s){
        if(s.length() == 0){
            result.add(new ArrayList<>(list));
            return;
        }
        for(int i = 0; i < s.length(); i++){
            if(panduan(s, 0, i)){
                list.add(s.substring(0,i+1));
                help(list, result, s.substring(i+1));
                list.remove(list.size() - 1);
            }
        }
    }
    
    private boolean panduan(String s, int start, int end){
        while(start < end){
            if(s.charAt(start++) != s.charAt(end--))
                return false;
        }
        return true;
    }
    
}

错误的答案 只是有这个想法 等Stringbuilder会用了再回来搞搞
class Solution {
    public List<List<String>> partition(String s) {
        List<List<String>> partitions = new ArrayList<>();
        List<String> partitionList = new ArrayList<>();
        StringBuilder sb = new StringBuilder;
        for(int i=1; i <= s.length(); i++)
            help();       
        return partitions;
    }
    private void help(List<List<String>> partitions, List<String> partitionList, 
         int size, StringBuilder sb){
        if(sb.length == size){
            if(isPalindrome(sb.toString, 0, sb.length - 1))
                partitions.add(new ArrayList<>(partitionList));
            return;
        }
        for(int i = start; i < s.length; i++){
            sb.append(s.charAt(i));
            help(partitions, partitionList, size, sb);
            patitionList.remove(partitionList.size() - 1);
        
        }
    }
    private boolean isPalindrome(String s, int start, int end){
        while(start < end){
            if(s.charAt(start++) != end.charAt(end--))
                return false;
        }    
        return true;
    }
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值