Given an input string (s
) and a pattern (p
), implement regular expression matching with support for ‘.‘
and ‘*‘
where:
给定一输入字符串 s
和匹配规则 p
,实现一个正则表达式引擎,要求能支持 ‘.‘
和 ‘*‘
的匹配,其中:
‘.‘
Matches any single character.‘.‘
匹配任意单个字符。????‘*‘
Matches zero or more of the preceding element.‘*‘
将其前面一个元素匹配 0 或多次。The matching should cover the entire input string (not partial).
匹配应该针对整个字符串进行(非部分)。
Input: s = "aa", p = "a"
Output: false
Explanation: "a" does not match the entire string "aa".
Input: s = "aa", p = "a*"
Output: true
Explanation: ‘*‘ means zero or more of the preceding element, ‘a‘. Therefore, by repeating ‘a‘ once, it becomes "aa".
Input: s = "ab", p = ".*"
Output: true
Explanation: ".*" means "zero or more (*) of any character (.)".
Input: s = "aab", p = "c*a*b"
Output: true
Explanation: c can be repeated 0 times, a can be repeated 1 time. Therefore, it matches "aab".
Input: s = "mississippi", p = "mis*is*p*."
Output: false
0 <= s.length <= 20
0 <= p.length <= 30
s
contains only lowercase English letters.p
contains only lowercase English letters, ‘.‘
, and ‘*‘
.‘*‘
, there will be a previous valid character to match.这题的做法有点像最长公共子序列。定义 dp(i, j)
表示 s[0, i]
和 p[0, j]
的匹配结果(字符串下标从 1 开始):
dp(0, 0) = true
(空串匹配空串);
若 s[i] == p[j]
,显然,dp(i, j) = dp(i - 1, j - 1)
;
若 p[j] == ‘.‘
,自然也能匹配,dp(i, j) = dp(i - 1, j - 1)
;
若 p[j] == ‘*‘
,则又有以下几种情况:
s[i] != p[j]
:则此时不能匹配任何字符,dp(i, j) = dp(i, j - 2)
s[i] == p[j]
或 p[j - 1] == ‘.‘
:此时以下三种情况都可以匹配
dp(i, j) = dp(i - 1, j)
(匹配多个字符)
dp(i, j) = dp(i, j - 1)
(匹配一个字符)
dp(i, j) = dp(i, j - 2)
(不匹配任何字符)
代码如下
class Solution {
fun isMatch(s: String, p: String): Boolean {
val dp = Array(s.length + 1) { BooleanArray(p.length + 1) }
dp[0][0] = true
for (i in p.indices) {
if (p[i] == ‘*‘ && dp[0][i - 1]) {
dp[0][i + 1] = true
}
}
for (i in s.indices) {
for (j in p.indices) {
doMatching(s, i, p, j, dp)
}
}
return dp.last().last()
}
private fun doMatching(
s: String,
i: Int,
p: String,
j: Int,
dp: Array<BooleanArray>
) {
if (p[j] == ‘.‘) {
dp[i + 1][j + 1] = dp[i][j]
}
if (p[j] == s[i]) {
dp[i + 1][j + 1] = dp[i][j]
}
if (p[j] == ‘*‘) {
if (p[j - 1] != s[i] && p[j - 1] != ‘.‘) {
dp[i + 1][j + 1] = dp[i + 1][j - 1]
} else {
dp[i + 1][j + 1] = (dp[i + 1][j] || dp[i][j + 1] || dp[i + 1][j - 1])
}
}
}
}
[LeetCode] 10. Regular Expression Matching(正则匹配)
原文:https://www.cnblogs.com/zhongju/p/14197001.html