• [Hot100]10. 正则表达式匹配


    10. 正则表达式匹配
    困难题
    动态规划:
    dp[i][j] 表示 s 的前 i 个是否能被 p 的前 j 个匹配

    ● 转移方程: 需要注意,由于 dp[0][0] 代表的是空字符的状态, 因此 dp[i][j] 对应的添加字符是 s[i - 1] 和 p[j - 1] 。
    ○ 当 p[j - 1] = ‘*’ 时, dp[i][j] 在当以下任一情况为 true时等于true :
    ■ dp[i][j-2]
    ● 将字符组合 p[j - 2] * 看作出现 0 次时,能否匹配;
    ■ dp[i-1][j]
    ● 且 p[j - 2] = s[i - 1]: 即让字符 p[j - 2]多出现 1 次时,能否匹配;
    ● 且 p[j - 2] = ‘.’:即让字符 ‘.’ 多出现 1 次时,能否匹配;

    ○ 当 p[j - 1] != ‘*’ 时, dp[i][j] 在当以下任一情况为true 时等于 true :
    ■ dp[i - 1][j - 1]
    ● 且 s[i - 1] = p[j - 1]: 即让字符 p[j - 1] 多出现一次时,能否匹配;
    ● 且 p[j - 1] = ‘.’: 即将字符 . 看作字符 s[i - 1] 时,能否匹配;

    class Solution {
        public boolean isMatch(String s, String p) {
            int m = s.length() + 1, n = p.length() + 1;
            boolean[][] dp = new boolean[m][n];
            dp[0][0] = true;
            // 初始化首行
            for(int j = 2; j < n; j += 2)
                dp[0][j] = dp[0][j - 2] && p.charAt(j - 1) == '*';
            // 状态转移
            for(int i = 1; i < m; i++) {
                for(int j = 1; j < n; j++) {
                    if(p.charAt(j - 1) == '*') {
                        if(dp[i][j - 2]) dp[i][j] = true;                                                          
                        // 1.
                        else if(dp[i - 1][j] && s.charAt(i - 1) == p.charAt(j - 2)) dp[i][j] = true; // 2.
                        else if(dp[i - 1][j] && p.charAt(j - 2) == '.') dp[i][j] = true;             // 3.
                    } else {
                        if(dp[i - 1][j - 1] && s.charAt(i - 1) == p.charAt(j - 1)) dp[i][j] = true;  // 1.
                        else if(dp[i - 1][j - 1] && p.charAt(j - 1) == '.') dp[i][j] = true;         // 2.
                    }
                }
            }
            return dp[m - 1][n - 1];
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    class Solution {
        public boolean isMatch(String s, String p) {
            int m = s.length();
            int n = p.length();
    
            boolean[][] f = new boolean[m + 1][n + 1];
            f[0][0] = true;
            for (int i = 0; i <= m; ++i) {
                for (int j = 1; j <= n; ++j) {
                    if (p.charAt(j - 1) == '*') {
                        f[i][j] = f[i][j - 2];
                        if (matches(s, p, i, j - 1)) {
                            f[i][j] = f[i][j] || f[i - 1][j];
                        }
                    } else {
                        if (matches(s, p, i, j)) {
                            f[i][j] = f[i - 1][j - 1];
                        }
                    }
                }
            }
            return f[m][n];
        }
    
        public boolean matches(String s, String p, int i, int j) {
            if (i == 0) {
                return false;
            }
            if (p.charAt(j - 1) == '.') {
                return true;
            }
            return s.charAt(i - 1) == p.charAt(j - 1);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
  • 相关阅读:
    解决du和df命令显示磁盘空间不一致的问题
    一看就会,使用 nginx 作为 HTTP 负载均衡器
    (二十一)大数据实战——Flume数据采集之复制和多路复用案例实战
    XXXSpringMVC“框架的简单创建与使用,快速上手;
    牛客刷题——剑指offer(第四期)
    金仓数据库KingbaseES客户端应用参考手册--19. vacuumlo
    最短路Dijkstra和最小生成树Prim算法的同异
    基础知识——进制 与 进制转换 (C++ 程序)
    关于深度图与鸟瞰图之间转换的问题
    Java代码质量评估工具
  • 原文地址:https://blog.csdn.net/m0_58058653/article/details/125529091