LeetCode 10. 正则表达式匹配

动态规划解题要考虑状态表示和状态计算
状态表示分为集合含义和输出属性
本题用 f ( i , j ) f(i,j) f(i,j)状态表示, s s s是原字符串, p p p是字符规律字符串
集合:所有 s [ 1 ∼ i ] s[1 \sim i] s[1i] p [ 1 ∼ j ] p[1 \sim j] p[1j]的匹配方案
属性:bool值,是否存在一个合法方案
状态计算
1.如果 p [ j ] ≠ ′ ∗ ′ p[j] \neq '*' p[j]=,那么 f ( i , j ) = ( s [ i ] = = p [ j ] ∣ ∣ p [ j ] = = ′ . ′ ) & & f [ i − 1 , j − 1 ] f(i, j) = (s[i] == p[j] || p[j] == '.') \& \& f[i-1, j-1] f(i,j)=(s[i]==p[j]p[j]==.)&&f[i1,j1]
2.如果 p [ j ] = = ′ ∗ ′ p[j] == '*' p[j]==,那么需要枚举匹配0个字符,1个字符, 匹配2个字符…
f ( i , j − 2 ) ∣ f ( i − 1 , j − 2 ) & s [ i ] = = p [ j ] ∣ f ( i − 2 , j − 2 ) & s [ i ] = = p [ j ] & s [ i − 1 ] = = p [ j − 1 ] ∣ . . . f(i, j - 2) | f(i - 1, j - 2) \& s[i] == p[j] | f(i-2, j-2) \& s[i] == p[j] \& s[i - 1] == p[j - 1]|... f(i,j2)f(i1,j2)&s[i]==p[j]f(i2,j2)&s[i]==p[j]&s[i1]==p[j1]...
状态数量是 O ( n 2 ) O(n^2) O(n2),转移全部枚举一遍所以是 O ( n ) O(n) O(n)。整个时间复杂度是 O ( n 3 ) O(n^3) O(n3)
这个式子没办法被计算机求解,后来发现
LeetCode 10. 正则表达式匹配_第1张图片
所以,总结规律 f ( i , j ) = f ( i , j − 2 ) ∣ f ( i − 1 , j ) & s i = = p j f(i, j) = f(i, j - 2) | f(i - 1, j) \& s_i == p_j f(i,j)=f(i,j2)f(i1,j)&si==pj

class Solution {
     
public:
    bool isMatch(string s, string p) {
     
        int n = s.size(), m = p.size();
        s = ' ' + s, p = ' ' + p;
        vector<vector<bool>> f(n + 1, vector<bool>(m + 1));
        f[0][0] = true;

        for(int i = 0; i <= n; i ++){
     
            for(int j = 1; j <= m; j ++){
     
                if(j + 1 <= m && p[j + 1] == '*') continue;
                if(i && p[j] != '*'){
     
                    f[i][j] = f[i - 1][j - 1] && (s[i] == p[j] || p[j] == '.');
                }else if(p[j] == '*'){
     
                    if(j == 1) continue;
                    f[i][j] = f[i][j - 2] || i && f[i - 1][j] && (s[i] == p[j - 1] || p[j - 1] == '.');
                }
            } 
        }
        return f[n][m];
    }
};

你可能感兴趣的:(LeetCode)