天天一道Rust-LeetCode(2019-06-04)

天天一道Rust-LeetCode(2019-06-04) 最長迴文子串

堅持天天一道題,刷題學習Rust.
原題git

題目描述

給定一個字符串 s,找到 s 中最長的迴文子串。你能夠假設 s 的最大長度爲 1000。github

示例 1:工具

輸入: "babad"
輸出: "bab"
注意: "aba" 也是一個有效答案。
示例 2:學習

輸入: "cbbd"
輸出: "bb"code

解題過程

思路:
怎麼把規模大的問題化成規模小的問題進行解決
假設用m[i][j]表示從i到j是迴文的長度
那麼只有兩種狀況能夠擴展出迴文
m[i][j]是迴文,當且僅當:ci

  1. m[i][j-1]是迴文,而且m[i][j-1]長度是1,而且m[j-1]==m[j]
  2. m[i+1][j-1]是迴文,而且m[i]==m[j]
    遍歷的過程當中記一個最長字符串便可.

還有另一種思路:
從中間向兩邊擴展
針對每一個字符,不斷向兩邊擴展以兩種形式aa,a向外擴展
第一種思路是O(n^2)複雜度
第二種差很少也是O(n^2)複雜度,考慮到剪枝效果,會高几倍
可是根據別人提交leetcode

struct Solution {}
impl Solution {
    pub fn longest_palindrome(s: String) -> String {
        if s.len() <= 0 {
            return s;
        }
        let ss = s.as_bytes();
        let mut m = vec![vec![0; ss.len()]; ss.len()];

        //        for i in 0..m.len() {
        //            m[i] = Vec::with_capacity(s.len());
        //        }
        for i in 0..m.len() {
            m[i][i] = 1; //自身確定是一個迴文
        }
        let mut longest = &ss[0..1];
        //step
        for k in 1..s.len() {
            //元素下標
            for i in 0..s.len() {
                if (i + k) < s.len() && m[i][i + k - 1] == 1 && ss[i + k - 1] == ss[i + k] {
                    m[i][i + k] = 2;
                    if longest.len() <= k {
                        longest = &ss[i..(i + k + 1)]; //包含最後一位
                    }
                } else {
                    let s = i + 1;
                    let e = i + k - 1;
                    if i + 1 >= m.len() || i + k >= m.len() {
                        continue; //越界的不考慮
                    }
                    if m[i + 1][i + k - 1] > 0 && ss[i] == ss[i + k] {
                        m[i][i + k] = m[i + 1][i + k - 1] + 2; //向周邊擴展了兩位
                        if longest.len() <= k {
                            longest = &ss[i..(i + k + 1)]; //包含最後一位
                        }
                    }
                }
            }
        }
        String::from_utf8(Vec::from(longest)).ok().unwrap()
    }
}

#[cfg(test)]
mod test {
    use super::*;
    #[test]
    fn test_longest_palindrome() {
        assert_eq!(Solution::longest_palindrome(String::from("babad")), "bab");
        assert_eq!(Solution::longest_palindrome(String::from("babba")), "abba");
        assert_eq!(Solution::longest_palindrome(String::from("abcdef")), "a");
        assert_eq!(Solution::longest_palindrome(String::from("")), "");
        assert_eq!(Solution::longest_palindrome(String::from("abbcd")), "bb");
    }
}

一點感悟

`String::from_utf8(Vec::from(longest)).ok().unwrap() `字符串之間的轉換仍是不太熟悉,
 基本工具使用不夠熟練

其餘

歡迎關注個人github,本項目文章全部代碼均可以找到.字符串

相關文章
相關標籤/搜索