当前位置: 首页 > article >正文

【困难】字符串匹配问题-Java:递归解法

分享一个大牛的人工智能教程。零基础通俗易懂风趣幽默希望你也加入到人工智能的队伍中来请轻击人工智能教程大家好欢迎来到我的网站 人工智能被认为是一种拯救世界、终结世界的技术。毋庸置疑人工智能时代就要来临了科… 继续阅读 前言https://www.captainai.net/troubleshooterpackage live.every.day.ProgrammingDesign.CodingInterviewGuide.String; /** * 字符串匹配问题 * * 【题目】 * 给定字符串str其中绝对不含有字符.和*。再给定字符串exp其中可以含有.或**字符不能是exp的首字符并且 * 任意两个*字符不相邻。exp中的.代表任何一个字符exp中的*表示*的前一个字符可以有0个或者多个。请写一个函数 * 判断str是否能被exp匹配。 * * 【难度】 * 困难 * * 【解答】 * 首先解决str和exp有效性的问题。根据描述str中不能含有.和*exp中*字符不能是首字符并且任意两个*字符不相 * 邻。具体请参看如下代码中的isValid方法。 * * 接下来看如何用递归方法来解这道题如下代码中的isMatch方法是递归解法的主函数process方法是递归的主要过程先列出代 * 码然后详细解释过程。 * * 下面解释一下递归过程process函数的意义是从str的si位置开始一直到str结束位置的子串即str[si..slen]是否能被 * 从exp的ei位置开始一直到exp结束位置的子串(即exp[ei..elen])匹配所以process(s,e,0,0)就是最终返回的结果。 * 那么在递归过程中如何判断str[si..slen]是否能被exp[ei..elen]匹配呢 * 假设当前判断到str的si位置和exp的ei位置即process(s,e,si,ei)。 * * 1.如果ei为exp的结束位置(eielen)si也是str的结束位置返回true因为可以匹配。如果si不是str的结束位置返 * 回false这是显而易见的。 * * 2.如果ei位置的下一个字符(e[ei1)不为*。那么就必须关注str[si]字符能否和exp[ei]字符匹配。如果str[si]与exp[ei] * 能匹配(e[ei]s[si]||e[ei].)还要关注str后续的部分能否被exp后续的部分匹配即process(s,e,si1,ei1)的 * 返回值。如果str[si]与exp[ei]不能匹配当前字符都匹配当然不用计算后续的直接返回false。 * * 3.如果当前ei位置的下一个字符(e[ei1])为*字符。 * 1)如果str[si]与exp[ei]不能匹配那么只能让exp[ei..ei1]这个部分为也就是exp[ei1]*字符的前一个字符 * exp[ei]的数量为0才行然后考查process(s,e,si,ei2)的返回值。 * 2)如果str[si]与exp[ei]能匹配exp[ei..ei1]的部分如果能匹配str后续很多位置的时候只要有一个返回true就可以直 * 接返回true。 * * 整体递归过程结束。 * * 在分析完如上递归过程之后来看递归函数的结构。我们很容易发现递归两数process(s,e,si,ei)在每次调用的时候有两个参数 * 是始终不变的(s和e)所以代表process函数状态的就是si和ei值的组合。所以如果把递归函数p在所有不同参数(si和ei)的情 * 况下的所有返回值看作一个范围这个范围就是一个(slen1)*(elen1)的二维数组并且p(si,ei)在整个递归过程中依赖的总 * 是p(sil,ei1)或者p(sik(k0),ei2)假设二维数组dp[i][j]代表p(i,j)的返回值dp[i][j]就只是依赖 * dp[i1][j1]或者dp[ik(k0)][j2]的值。进一步可以看出想要求dp[i][j]的值只需要(i,j)位置右下方的某些值。所 * 以只要从二维数组的右下角开始从右到左、再从下到上地计算出二维数组dp中每个位置的值就可以dp[0][0]就是最终的结果。 * p(i,j)的递归过程如何dp[i,j]的值就怎样去计算。这种方法实际上就是动态规划的方法省去了递归过程中很多重复计算的过程。 * * 先从右到左计算dp[slen][...]也就是二维数组dp中的最后一行dp[slen][elen]值的含义是str已经结束剩下的宇符串为 * exp也已经结束剩下的字符串为所以此时exp可以匹配strdp[slen][elen]true。对于dp[slen][0..elen-1]的 * 部分dp[slen][i]的含义是str已经结束剩下的字符串为exp却没有结束剩下的字符串为exp[i..elen-1]什么情况下 * exp[i..elen-1]可以匹配只能是不停地重复出现X*知这种方式。也就是说在从右向左计算dp[slen][0..elen-1]的过 * 程中看exp是不是从右往左重复出现X*如果是重复出现那么如果exp[i]Xexp[i1]*令dp[slen][i]true * 如果exp[i]*exp[i1]X令dp[slen][i]false。如果不是重复出现最后一行后面的部分(即dp[slen][0..i]) * 全都是false。这样就搞定了dp[][]最后一行的值。 * * 再看看dp[][]除右下角的值之外最后一列其他位置的值即dp[0..slen-1][elen]。这表示如果exp已经结束而str还没结 * 束显然exp为匹配不了任何非空字符串所以dp[0..slen-1][elen]都为false。 * * 接着看dp[][]倒数第二列的值即dp[0..slen-1][elen-1]。这表示如果exp还剩一个字符即(exp[elen-1])而str还剩1个 * 字符或多个字符。很明显str还剩多个字符的情况下exp匹配不了。str还剩1个字符的情況下(即str[slen-1])如果和 * exp[elen-1]相等则可以匹配或者exp[elen-1].的情况下可以匹配。 * * 因为dp[i][j]只依赖dp[i1][j1]或者dp[ik][j2](k0)的值所以在单独计算完最后一行、最后一列与倒数第二列之后 * 剩下的位置在从右到左、再从下到上计算dp值的时候所有依赖的值都被计算出来直接拿过来用即可。如果str的长度为Nexp的 * 长度为M因为有枚举的过程所以时间复杂度为O(N^2×M)额外空间复杂度为O(NXM)。 * * 具体请参看如下代码中的isMatchDP方法。 * * author Created by LiveEveryDay */ public class StringMatchProblem1 { public static boolean isValid(char[] s, char[] e) { for (int i 0; i s.length; i) { if (s[i] * || s[i] .) { return false; } } for (int i 0; i e.length; i) { if (e[i] * (i 0 || e[i - 1] *)) { return false; } } return true; } public static boolean isMatch(String str, String exp) { if (str null || exp null) { return false; } char[] s str.toCharArray(); char[] e exp.toCharArray(); return isValid(s, e) ? process(s, e, 0, 0) : false; } public static boolean process(char[] s, char[] e, int si, int ei) { if (ei e.length) { return si s.length; } if (ei 1 e.length || e[ei 1] ! *) { return si ! s.length (e[ei] s[si] || e[ei] .) process(s, e, si 1, ei 1); } while (si ! s.length (e[ei] s[si] || e[ei] .)) { if (process(s, e, si, ei 2)) { return true; } si; } return process(s, e, si, ei 2); } public static void main(String[] args) { String str cdCCDDEE; String exp c.C*D*E*; System.out.printf(Does it match? %b, isMatch(str, exp)); } } // ------ Output ------ /* Does it match? true */

相关文章:

【困难】字符串匹配问题-Java:递归解法

分享一个大牛的人工智能教程。零基础!通俗易懂!风趣幽默!希望你也加入到人工智能的队伍中来!请轻击人工智能教程大家好!欢迎来到我的网站! 人工智能被认为是一种拯救世界、终结世界的技术。毋庸置疑&#x…...

如何在浏览器中实现专业级Markdown文档实时渲染:完整配置指南

如何在浏览器中实现专业级Markdown文档实时渲染:完整配置指南 【免费下载链接】markdown-viewer Markdown Viewer / Browser Extension 项目地址: https://gitcode.com/gh_mirrors/ma/markdown-viewer Markdown Viewer是一款功能强大的浏览器扩展&#xff0c…...

RPG Maker MV/MZ游戏资源解密工具:5分钟解锁游戏素材的完整指南

RPG Maker MV/MZ游戏资源解密工具:5分钟解锁游戏素材的完整指南 【免费下载链接】RPG-Maker-MV-Decrypter You can decrypt RPG-Maker-MV Resource Files with this project ~ If you dont wanna download it, you can use the Script on my HP: 项目地址: https:…...

iOS激活锁完美绕过:AppleRa1n完整教程与操作指南

iOS激活锁完美绕过:AppleRa1n完整教程与操作指南 【免费下载链接】applera1n icloud bypass for ios 15-16 项目地址: https://gitcode.com/gh_mirrors/ap/applera1n 如果您正面临iPhone设备被激活锁困扰的困境,这篇AppleRa1n完整指南将为您提供专…...

BiliTools终极指南:2026年最强大的免费哔哩哔哩下载工具

BiliTools终极指南:2026年最强大的免费哔哩哔哩下载工具 【免费下载链接】BiliTools A cross-platform bilibili toolbox. 跨平台哔哩哔哩工具箱,支持下载视频、番剧等等各类资源 项目地址: https://gitcode.com/GitHub_Trending/bilit/BiliTools …...

如何免费解锁Cursor AI Pro功能:终极三步激活指南

如何免费解锁Cursor AI Pro功能:终极三步激活指南 【免费下载链接】cursor-free-vip [Support 0.45](Multi Language 多语言)自动注册 Cursor Ai ,自动重置机器ID , 免费升级使用Pro 功能: Youve reached your trial r…...

桌面整理神器:NoFences让你的Windows桌面焕然一新 [特殊字符]

桌面整理神器:NoFences让你的Windows桌面焕然一新 🚀 【免费下载链接】NoFences 🚧 Open Source Stardock Fences alternative 项目地址: https://gitcode.com/gh_mirrors/no/NoFences 你是不是也厌倦了Windows桌面上杂乱无章的图标&a…...

信步NSE SVX-C2304嵌入式主板拆解:Elkhart Lake平台在工业边缘计算的应用

1. 项目概述:一块嵌入式主板的深度拆解最近在整理一个工业边缘计算项目的硬件选型方案,手头拿到了一块信步科技(Seavo)的NSE SVX-C2304嵌入式主板。这名字听起来可能有点“板正”,不像消费级产品那样花哨,但…...

JavaScript 的速度秘密:深入理解 JIT (即时编译)

⚡ JavaScript 的速度秘密:深入理解 JIT (即时编译) 🤔 为什么 JavaScript 能这么快? 在早期,JavaScript 是一种解释型语言。浏览器逐行读取代码,翻译成机器指令并执行。这种方式启动快,但运行慢&#xf…...

递归的终极形态:彻底搞懂尾递归优化 (TCO)

🔄 递归的终极形态:彻底搞懂尾递归优化 (TCO) 🤔 为什么普通递归会“爆栈”? 在理解尾递归之前,先看看普通递归发生了什么。 通俗比喻: 想象你在玩一个“传话游戏”,需要计算 1 2 3 ... n…...

如何让Windows资源管理器完美预览iPhone照片:HEIC缩略图插件全解析

如何让Windows资源管理器完美预览iPhone照片:HEIC缩略图插件全解析 【免费下载链接】windows-heic-thumbnails Enable Windows Explorer to display thumbnails for HEIC/HEIF files 项目地址: https://gitcode.com/gh_mirrors/wi/windows-heic-thumbnails 你…...

如何使用witr快速定位占用端口的神秘进程?完整指南

如何使用witr快速定位占用端口的神秘进程?完整指南 【免费下载链接】witr Why is this running? 项目地址: https://gitcode.com/GitHub_Trending/wi/witr 你是否曾经遇到过端口被占用却不知道是哪个进程在捣乱的情况?😫 想要启动Web…...

Deepin Boot Maker终极指南:3分钟制作完美启动盘的免费神器

Deepin Boot Maker终极指南:3分钟制作完美启动盘的免费神器 【免费下载链接】deepin-boot-maker 项目地址: https://gitcode.com/gh_mirrors/de/deepin-boot-maker 你是否曾经为了制作系统启动盘而烦恼?面对复杂的命令行工具,担心误操…...

Oto 核心架构深度解析:Context 与 Player 的设计哲学

Oto 核心架构深度解析:Context 与 Player 的设计哲学 【免费下载链接】oto ♪ A low-level library to play sound on multiple platforms ♪ 项目地址: https://gitcode.com/gh_mirrors/ot/oto Oto 是一个跨平台的低级音频播放库,其核心架构围绕…...

zen-rails-security-checklist测试策略:安全测试用例与自动化扫描

zen-rails-security-checklist测试策略:安全测试用例与自动化扫描 【免费下载链接】zen-rails-security-checklist Checklist of security precautions for Ruby on Rails applications. 项目地址: https://gitcode.com/gh_mirrors/ze/zen-rails-security-checkli…...

3个常见视频下载难题,猫抓扩展如何帮你一键解决?浏览器资源嗅探实战指南

3个常见视频下载难题,猫抓扩展如何帮你一键解决?浏览器资源嗅探实战指南 【免费下载链接】cat-catch 猫抓 浏览器资源嗅探扩展 / cat-catch Browser Resource Sniffing Extension 项目地址: https://gitcode.com/GitHub_Trending/ca/cat-catch 你…...

内容创作团队如何利用多模型API提升图文生成效率

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 内容创作团队如何利用多模型API提升图文生成效率 对于新媒体运营、电商内容或市场团队而言,持续产出高质量的图文内容是…...

MKS Robin Nano Marlin 2.0固件架构解析与性能调优指南

MKS Robin Nano Marlin 2.0固件架构解析与性能调优指南 【免费下载链接】Mks-Robin-Nano-Marlin2.0-Firmware The firmware of Mks Robin Nano, based on Marlin-2.0.x, adding the color GUI. 项目地址: https://gitcode.com/gh_mirrors/mk/Mks-Robin-Nano-Marlin2.0-Firmwa…...

WinForm用户控件调试踩坑记:从‘无法试运行’到完美模块测试的完整流程

WinForm用户控件调试实战:从模块移植到精准测试的完整指南 引言:为什么需要独立的控件测试环境? 在WinForm开发中,用户控件(UserControl)的复用与调试一直是让开发者头疼的问题。当你在主项目中直接测试一个复杂控件时&#xff0c…...

Windows资源管理器STL缩略图革命:3D模型可视化管理的终极解决方案

Windows资源管理器STL缩略图革命:3D模型可视化管理的终极解决方案 【免费下载链接】STL-thumbnail Shellextension for Windows File Explorer to show STL thumbnails 项目地址: https://gitcode.com/gh_mirrors/st/STL-thumbnail 还在为海量STL文件的管理而…...

5分钟打造专业级抽奖系统:Magpie-LuckyDraw全平台使用终极指南

5分钟打造专业级抽奖系统:Magpie-LuckyDraw全平台使用终极指南 【免费下载链接】Magpie-LuckyDraw 🏅A fancy lucky-draw tool supporting multiple platforms💻(Mac/Linux/Windows/Web/Docker) 项目地址: https://gitcode.com/gh_mirrors/…...

Aspose全家桶实战:从零构建一个.NET 6的文档转换微服务(含Docker部署)

Aspose全家桶实战:从零构建.NET 6文档转换微服务 在数字化转型浪潮中,企业文档处理需求正经历从碎片化到集中化的转变。传统单体应用中分散的Word转PDF、Excel报表生成等功能,不仅难以维护,更无法适应云原生时代对弹性伸缩和高可用…...

Unity问题记录

一个物体在Scene窗口看不见,Game窗口能看见。选中它时,打开Gizmos也看不见身上碰撞体的线框。也无法被射线检测到。换成其他Mesh:Open Asset In Context正常显示:把它Revert回预制体,还是不显示。Ctrl D复制一个&#…...

Cursor AI编程助手扩展包:定制化规则提升代码生成质量与效率

1. 项目概述:一个为 Cursor 编辑器量身定制的 AI 编程助手扩展包如果你和我一样,日常重度依赖 Cursor 这款“AI 驱动的代码编辑器”来提升开发效率,那你肯定不止一次地想过:能不能让 Cursor 更懂我?能不能让它在我写特…...

从零搭建到日常调试:一份给新手的 Kafka 命令行操作全流程指南

从零搭建到日常调试:一份给新手的 Kafka 命令行操作全流程指南 第一次接触 Kafka 时,我被它那些晦涩的概念和复杂的命令行参数搞得晕头转向。作为一个从 MySQL 和 Redis 这类传统数据库转过来的开发者,Kafka 的分布式消息队列模型确实需要一些…...

DESIGN.md,让AI设计不跑偏

使用 AI 设计工具时,最烦人的问题之一,就是输出不稳定。你明明已经告诉它:颜色怎么用、字体怎么搭、按钮要什么风格。可它生成几次之后,还是会偷偷改一点,最后做出来的界面风格前后不一致。DESIGN.md 就是为了解决这个…...

ASO技能库构建指南:从基础原理到实战应用

1. 项目概述:ASO技能库的构建与价值最近在和一些做独立开发者和出海应用推广的朋友聊天,大家普遍提到一个痛点:都知道ASO(应用商店优化)重要,但真到动手优化自家App的时候,却感觉无从下手。市面…...

用C++和Eigen库手把手实现UR3机械臂逆解(附完整代码与避坑指南)

从理论到实践:基于Eigen库的UR3机械臂逆运动学完整实现指南 在工业自动化和机器人研究领域,六轴协作机械臂因其灵活性和广泛的应用场景而备受关注。UR3作为Universal Robots旗下的紧凑型协作机械臂,凭借其轻量化设计和用户友好特性&#xff0…...

DLT Viewer:面向汽车电子系统的分布式日志诊断与实时监控技术方案

DLT Viewer:面向汽车电子系统的分布式日志诊断与实时监控技术方案 【免费下载链接】dlt-viewer Diagnostic Log and Trace viewing program 项目地址: https://gitcode.com/gh_mirrors/dl/dlt-viewer DLT Viewer是一款基于COVESA标准的专业诊断日志分析工具&…...

Git 核心操作:rebase 与 merge 的区别,以及分支管理最佳实践

Git 核心操作:rebase 与 merge 的区别,以及分支管理最佳实践 在日常开发中,Git 是不可或缺的版本控制工具。而 git merge 和 git rebase 是整合分支最常用的两个命令,很多人对它们的概念模糊,不知道何时用哪个。同时&a…...