Leetcode:Regular Expression Matching 正则匹配

戳我去解题

Implement regular expression matching with support for '.' and '*'.



'.' Matches any single character.

'*' Matches zero or more of the preceding element.



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



The function prototype should be:

bool isMatch(const char *s, const char *p)



Some examples:

isMatch("aa","a") → false

isMatch("aa","aa") → true

isMatch("aaa","aa") → false

isMatch("aa", "a*") → true

isMatch("aa", ".*") → true

isMatch("ab", ".*") → true

isMatch("aab", "c*a*b") → true

 



class Solution {

public:

    bool isMatch(const char *s, const char *p) {

         assert(s != NULL && p != NULL);

         if (*p == '\0') return *s == '\0';

         

         // next char is not '*'; must match current character 

         if (*(p+1) != '*') {

             assert(*p != '*');

             return ((*p == *s) || (*p == '.' && *s != '\0')) && isMatch(s+1, p+1);

         }

         

         // necx char is '*'

         while ((*p == *s) || (*p == '.' && *s != '\0')) {

             if (isMatch(s, p+2)) {

                 return true;

             }

             s++;

         }

         return isMatch(s, p+2);

    }

};

对于s和p,首先我们知道正则匹配模式串中的单个字符(排除'*')时,一定是以下两种情况之一:

(1) *p == *s



(2) *p == '.'  && *s != '\0'

我们再来逐个分析模式串:

首先对于模式串中的第一个字符:因为该字符之后是否为'*' 两种匹配方法完全不同,这时我们分两种情况考虑:

(1) 当其后不为'*'时,那么我们直接匹配该字符(两种情况之一) 和 该字符之后的子串(使用递归,isMatch(s+1, p+1) )

注意 不能出现 '*a' 这种情况,所以有个assert(*p != '*')

 

(2) 当其后为'*'时,例如 'a*' , 因为'*'表示可以匹配0个或多个'a', 所以我们一直循环匹配a 直到未匹配a 为止 (匹配一个字符一定是上面所说的两种情况之一)

循环匹配重复字符时,我们需要做两件事:

a. 更新s,使得匹配字符一直向前移动

b. 使用递归判断子串是否正则匹配 isMatch(s, p+2)  //  这里s是更新过后的新起始位置,p+2 表示跳过'a*'两个字符之后的子串

 

注意对于'a*' 可能会出现一个a也没有匹配到(匹配0次),也就是循环没有执行,这时我们就接下来正则匹配子串 isMatch(s, p+2)

 

你可能感兴趣的:(Leetcode:Regular Expression Matching 正则匹配)