题目描述
请实现一个函数用来匹配包括’.’和’‘的正则表达式。模式中的字符’.’表示任意一个字符,而’‘表示它前面的字符可以出现任意次(包含0次)。 在本题中,匹配是指字符串的所有字符匹配整个模式。例如,字符串”aaa”与模式”a.a”和”ab*ac*a”匹配,但是与”aa.a”和”ab*a”均不匹配
后来,我自己写了一遍,发现是有一些逻辑的。
(1)以两数组指针的位置为判断基准,当两指针都指向数组最后一位的下一位,说明匹配(当最后一位匹配的话,肯定要往后移动一位);
(2)若str尚未到最后一位,但模式串中到了最后一位,此时肯定不匹配;
(3)若str到了最后一位,模式串尚未到最后,此时,模式串只有p+1指针位置的字符判断机会,如果是“*”的话,它可以表示0个,那么此时匹配;否则不匹配;
(4)然后判断当模式串的下一位是“ * ”的时候,如果str的当前位和模式串的当前位字符相等,那么有三种情况:前数字出现的次数分别是0,1,多次;如果不相等,那么只有当“ ”出现次数为0的时候,可能为匹配(只是可能),接着匹配模式串的下两位;否则不匹配;
(5)当当前位相等,或者模式串的字符为‘ . ’的时候,接着匹配下一位;
注意:第(4)步是预判断下一位,因此,要早于第五步。
public class Solution {
public boolean matchCode(char[] str, int s,char[] pattern,int p){
if(s == str.length && p == pattern.length)
return true;
if(s < str.length && p == pattern.length)
return false;
if(s == str.length && p < pattern.length){
if(p+1 == pattern.length-1 && pattern[p+1]=='*'){
return true;
}
return false;
}
if(p+1< pattern.length && pattern[p+1] == '*'){
if(str[s] == pattern[p] || pattern[p] == '.'){
return matchCode(str,s,pattern,p+2) || matchCode(str,s+1,pattern,p+2) || matchCode(str,s+1,pattern,p);
}else if(str[s] != pattern[p]){
return matchCode(str,s,pattern,p+2);
}
return false;
}
if(s< str.length && p<pattern.length && (str[s] == pattern[p] || pattern[p] == '.')){
return matchCode(str,s+1,pattern,p+1);
}
return false;
}
public boolean match(char[] str, char[] pattern)
{
if(str == null || pattern == null)
return false;
return matchCode(str,0,pattern,0);
}
}
注意了:必须先判断“ * ”的情况,然后再判断“ . ”的情况。==》案例:“aa”,“a*”
因为“ * ”可能代表着0个,这样的话,当前位可能就不存在了,比较“.”没有意义。
上述案例,如果先比较“ . ”的话,第一轮都向前移动1,第二轮直接比较‘a’ 和 ‘’了,这样的话,‘’前面的位置过去了,就没有比较的必要了。因为‘*’可能是0,1,2,3。。。的多样性不能表示出来。
public class Solution {
public boolean matchCore(char[] str,int strIndex,char[] pattern,int patternIndex){
if((strIndex == str.length) && (patternIndex == pattern.length))
return true;
if((strIndex != str.length) && (patternIndex == pattern.length))
return false;
if(strIndex==str.length && patternIndex != pattern.length) {
while(patternIndex != pattern.length){
if(pattern[patternIndex]!='*' && (patternIndex+1>=pattern.length||pattern[patternIndex+1]!='*')){
return false;
}
patternIndex++;
}
return true;
}
if((patternIndex+1 < pattern.length) && (pattern[patternIndex+1] == '*')){
if((str[strIndex] == pattern[patternIndex]) || (pattern[patternIndex] == '.')){
return matchCore(str,strIndex + 1,pattern,patternIndex + 2)
|| matchCore(str,strIndex + 1,pattern,patternIndex)
|| matchCore(str,strIndex,pattern,patternIndex + 2);
}else{
return matchCore(str,strIndex,pattern,patternIndex + 2);
}
}
if((str[strIndex] == pattern[patternIndex]) || (pattern[patternIndex] == '.')){
return matchCore(str,strIndex + 1,pattern,patternIndex + 1);
}
return false;
}
public boolean match(char[] str, char[] pattern)
{
if(str == null || pattern == null)
return false;
int strIndex = 0;
int patternIndex = 0;
return matchCore(str,strIndex,pattern,patternIndex);
}
}