leetcode 正则表达式匹配 困难
Posted Wh1t3zZ
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了leetcode 正则表达式匹配 困难相关的知识,希望对你有一定的参考价值。
题目:https://leetcode-cn.com/problems/regular-expression-matching/
动态规划:dp[i][j] 表示 s 串前 i 个 与 p 串前 j 个是否能够成功匹配。
状态转移方程不难:
if(s[i] == p[j] || p[j] == \'.\') dp[i][j] = dp[i - 1][j - 1];
if(p[j] == \'*\') {
dp[i][j] = dp[i][j - 2]; // * 前面一个字符使用个数为 0
if(s[i] == p[j - 1] || p[j - 1] == \'.\') dp[i][j] = (dp[i][j] | dp[i - 1][j] | dp[i - 1][j - 1]); // 分别表示 * 使用的个数 >1 与 * 使用的个数 == 1.
}
不过需要特别注意边界的问题:如 "", "a*" 中,是能够匹配成功的。所以循环遍历是 s 串在前,就不好处理。
这里将 i 与 j 的意义调换,先循环 p 串,再循环 s 串,因为 p 串为空的情况更简单。(并且,为了处理 状态转移中下标 -1 导致越界的问题,横纵统一做一个单位偏移量)
class Solution { public: bool isMatch(const string &s, const string &p) { vector<vector<bool>> dp(p.size() + 1, vector<bool>(s.size() + 1, false)); dp[0][0] = true; for(int i = 0; i < p.size(); ++ i) { if(p[i] == \'*\') { dp[i + 1][0] = dp[i - 1][0]; // dp[i][0] = dp[i - 2][0]. 注意这一行的状态不要漏掉了. } for(int j = 0; j < s.size(); ++ j) { if(p[i] == s[j] || p[i] == \'.\') { dp[i + 1][j + 1] = dp[i][j]; // dp[i][j] = dp[i - 1][j - 1]; } else if(p[i] == \'*\') { if(p[i - 1] == \'.\' || p[i - 1] == s[j]) { dp[i + 1][j + 1] = (dp[i][j] | dp[i + 1][j]); // dp[i][j] = dp[i - 1][j - 1] | dp[i][j - 1]; // 使用 1 个, 或继续使用 * } dp[i + 1][j + 1] = (dp[i + 1][j + 1] | dp[i - 1][j + 1]); // dp[i][j] = dp[i - 2][j]; // * 为 0 个 } } } return dp.back().back(); } };
以上是关于leetcode 正则表达式匹配 困难的主要内容,如果未能解决你的问题,请参考以下文章