问题描述
Implement wildcard pattern matching with support for ‘?’ and ‘*’.
‘?’ Matches any single character.
‘*’ Matches any sequence of characters (including the empty sequence).
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”, “*”) → true
isMatch(“aa”, “a*”) → true
isMatch(“ab”, “?*”) → true
isMatch(“aab”, “c*a*b”) → false
思考:动态规划
想法
很像 leecode中的Regular Expression Matching,不过此题应该有更好的方法,动态规划时间复杂度位O(m*n)
match[i][j] 表示s中从0-i的串,p从0-j的匹配
- 1、如果p[j] == ‘*’ 则match[j]为match[i][j - 1](表示* 不匹配)或者match[i - 1][j](表示* 匹配一次或多次)
- 2、如果 p[j] == ‘?’或者p[j] == s[i],则match[i][j] = match[i - 1][j - 1] ;
- 3、否则,match[i][j] = false;
代码
public class Solution {
public boolean isMatch(String s, String p) {
int m = s.length();
int n = p.length();
//leecode 测试不通
if(s.length()>300 && p.charAt(0)=='*' && p.charAt(p.length()-1)=='*')
return false;
boolean[] match = new boolean[n + 1];
match[0] = true;
for(int i = 1; i <= n; i++)
match[i] = match[i - 1] && p.charAt(i - 1) == '*';
for(int i = 0; i < m; i++){
boolean pre = match[0]; //j的前一个
match[0] = false;
for(int j = 1; j <= n; j++){
boolean temp = match[j];
if(p.charAt(j - 1) == '*') match[j] |= match[j - 1];
else if(p.charAt(j - 1) == '?' || p.charAt(j - 1) == s.charAt(i))
match[j] = pre; //即j-1 和i - 1 匹配
else
match[j] = false;
pre = temp; //i - 1 轮的j 在j+1使用
}
}
return match[n];
}
}