经过前期的数据结构和算法学习,开始以OD机考题作为练习题,继续加强下熟练程度。
问题描述:在计算机中,通配符一种特殊语法,广泛应用于文件搜索、数据库、正则表达式等领域。现要求各位实现字符串通配符的算法。
要求:
实现如下2个通配符:
*:匹配0个或以上的字符(注:能被*和?匹配的字符仅由英文字母和数字0到9组成,下同)
?:匹配1个字符
注意:匹配时不区分大小写。
输入:
通配符表达式;
一组字符串。
输出:
返回不区分大小写的匹配结果,匹配成功输出true,匹配失败输出false
数据范围:字符串长度:1≤𝑠≤100 1≤s≤100
进阶:时间复杂度:𝑂(𝑛2) O(n2) ,空间复杂度:𝑂(𝑛) O(n)
先输入一个带有通配符的字符串,再输入一个需要匹配的字符串
返回不区分大小写的匹配结果,匹配成功输出true,匹配失败输出false
输入:
te?t*.* txt12.xls输出:
false
初始化:
dp[0][0]
表示空字符串和空模式匹配。p
的字符是'*'
,则dp[0][j]
的值取决于dp[0][j - 1]
,表示'*'
可以匹配空字符串。填充DP数组:
s
和模式p
的所有字符。'*'
,则dp[i][j]
可以由两种情况决定:
dp[i - 1][j]
:'*'
匹配一个或多个字符。dp[i][j - 1]
:'*'
匹配空字符串。'?'
或与字符串字符相等,则dp[i][j]
由dp[i - 1][j - 1]
决定,表示这两个字符匹配。返回结果:
dp[sLen][pLen]
,表示字符串s
和模式p
的匹配结果。此题为难度系数为中等略有不妥,另外需注意题干中?和*只能匹配数字和英文字母。
- import java.util.Scanner;
-
- // 注意类名必须为 Main, 不要有任何 package xxx 信息
- public class Main {
-
- public static void main(String[] args) {
- Scanner in = new Scanner(System.in);
- // 注意 hasNext 和 hasNextLine 的区别
- String p = in.nextLine();
- String s = in.nextLine();
- System.out.println(isMatch(s, p)); // 输出:true 或 false
-
- }
-
- public static boolean isMatch(String s, String p) {
- int sLen = s.length();
- int pLen = p.length();
-
- // 创建一个DP数组,dp[i][j]表示s的前i个字符和p的前j个字符是否匹配
- boolean[][] dp = new boolean[sLen + 1][pLen + 1];
-
- // 初始化
- dp[0][0] = true; // 空字符串和空模式是匹配的
-
- // 初始化首行,s为空,只有p全是'*'才能匹配
- for (int j = 1; j <= pLen; j++) {
- if (p.charAt(j - 1) == '*') {
- dp[0][j] = dp[0][j - 1];
- }
- }
-
- // 填充DP数组
- for (int i = 1; i <= sLen; i++) {
- for (int j = 1; j <= pLen; j++) {
- if (p.charAt(j - 1) == '*') {
- // '*' 可以匹配任意字符串(包括空字符串)
- //if(isNumOrWord(s.charAt(i-1))){
- dp[i][j] = dp[i - 1][j] || dp[i][j - 1];
- //}
- } else if ((p.charAt(j - 1) == '?' && isNumOrWord(s.charAt(i - 1))) ||
- Character.toString(s.charAt(i - 1)).equalsIgnoreCase(Character.toString(
- p.charAt(j - 1)))) {
- // '?' 可以匹配任意一个字符
- dp[i][j] = dp[i - 1][j - 1];
- }
- }
- }
-
- return dp[sLen][pLen];
- }
-
- public static boolean isNumOrWord(char c) {
- if (c - 'a' >= 0 && c - 'a' <= 26) {
- return true;
- } else if (c - '0' >= 0 && c - '0' <= 9) {
- return true;
- }
- return false;
- }
-
-
- }