简单的正则表达式匹配 Regular Expression Matching

142 篇文章 20 订阅
45 篇文章 0 订阅

题目源自于Leetcode。

只需要支持两个匹配符*和.。

'.' Matches any single character.
'*' Matches zero or more of the preceding element.

本题的要求是能够全部匹配整个母字符串,而不是包含有

The matching should cover the entire input string (not partial).


思路:母字符串和模式串双指针移动。会遇到最大的难点在于模式串遇到 .* 之后,母字符串该如何向后移动的问题,因为.*太灵活了,只有先知道之后的匹配情况才能对.* 进行适合的匹配,因此存在一个回溯的问题

把循环改成递归,是一种很常用的策略。

若当前问题可以判定结果,则返回判定结果;

若在当前问题无法确定、需要依赖于之后的问题的时候,使用返回递归来求解之后的问题。


代码:

class Solution {
public:
    bool isMatch(const char *s, const char *p) 
    {   
        if (s == NULL || p == NULL) 
            return false;
        if (*p == '\0') 
            return *s == '\0';
     
        if (*(p + 1) == '*') //当前出现任意匹配
        {
            while ((*s != '\0' && *p == '.') || *s == *p) //出现.*
            {
                if (isMatch(s, p + 2)) 
                    return true;
                ++s;
            }
            return isMatch(s, p + 2);
        }
        else if ((*s != '\0' && *p == '.') || *s == *p) //当前是正常匹配or.匹配
        {
            return isMatch(s + 1, p + 1);
        }
        else //当前是错误匹配
            return false;
    }
};

代码注释:

比较关键的一处是第11行为什么要用while循环。

首先要知道while循环的是母字符串从当前位置开始~直到~遇到不匹配或结尾的所有字符。为什么要这样?因为正则匹配符*是任意次数的匹配,我自己并不知道到底应该匹配多少次,所以只能每一次可以的匹配都做一遍,即每个状态空间子树都尝试一下。这些状态空间子树,注定是失败居多,少数或唯一一个成功,只要有一个子树是匹配的,当前状态就是匹配的。


这个逻辑是挺难理解的,多看几次。递归思想+分治思想。

1、考虑递归结束条件,即最原子化的问题。

2、只关注当前问题,子问题交给递归来做。

 

 


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值