跳至主要內容

131, 分割回文串

Mike大约 2 分钟backtrackingmediumstringdynamic programmingbacktracking

一、题目描述

给你一个字符串s,请你将s分割成一些子串,使每个子串都是回文串。返回s所有可能的分割方案。

回文串是正着读和反着读都一样的字符串。

示例 1
输入: s = "aab"
输出: [["a", "a", "b"],["aa", "b"]]

示例 2
输入: s = "a"
输出: [["a"]]

提示

  • 1 <= s.length <= 16
  • s仅由小写英文字母组成

相关主题

  • 字符串
  • 动态规划
  • 回溯

二、题解

方法 1: 回溯

pub fn partition(s: String) -> Vec<Vec<String>> {
    const IS_PALINDROME: fn(&str) -> bool = |s| {
        let mut is_palindrome = true;
        let (mut i, mut j) = (0, s.len() - 1);

        while i < j {
            if &s[i..i + 1] != &s[j..j + 1] {
                is_palindrome = false;
            }
            (i, j) = (i + 1, j - 1)
        }

        is_palindrome
    };

    const DFS: for<'a> fn(usize, &'a str, &mut Vec<&'a str>, &mut Vec<Vec<String>>) =
        |i, s, combine, res| {
            if i == s.len() {
                res.push(combine.iter().map(|&s| s.to_string()).collect::<Vec<_>>());
                return;
            }

            for j in (i + 1)..=s.len() {
                let substring = &s[i..j];

                if IS_PALINDROME(substring) {
                    combine.push(substring);
                    DFS(j, s, combine, res);
                    combine.pop();
                }
            }
        };
    let mut res = vec![];

    DFS(0, &s, &mut vec![], &mut res);

    res
}

方法 2: 回溯 + 动态规划

pub fn partition(s: String) -> Vec<Vec<String>> {
    let len = s.len();
    let mut f = vec![vec![true; len]; len];

    for i in (0..len).rev() {
        for j in i + 1..len {
            f[i][j] = (&s[i..i + 1] == &s[j..j + 1]) && f[i + 1][j - 1];
        }
    }

    const DFS: fn(usize, &str, &mut Vec<String>, &mut Vec<Vec<String>>, &Vec<Vec<bool>>) =
        |i, s, combine, res, f| {
            if i == s.len() {
                res.push(combine.clone());
                return;
            }

            for j in i..s.len() {
                if f[i][j] {
                    combine.push(s[i..j + 1].to_string());
                    DFS(j + 1, s, combine, res, f);
                    combine.pop();
                }
            }
        };
    let mut res = vec![];

    DFS(0, &s, &mut vec![], &mut res, &f);

    res
}