字符串匹配 之 KMP算法

文章目录

本博客充分参考灵神和知乎的另一位博主

灵神KMP算法模版
知乎博主通俗易懂讲解

  • 对于给定一个主串S和一个模式串P,如果让你求解出模式串P在主串S中匹配的情况下的所有的开始下标
  • 简单的做法又称为Brute-Force算法,其实总的来说就是,外层循环遍历主串S,内存循环遍历模式串P,逐个匹配,当出现匹配不成功的情况,外层循环回到开始匹配位置+1,内层循环直接返回位置0,可想而知,这个算法的时间复杂度是o(n*m)
  • KMP算法的改进思路,就是比较的时候,肯定是一个个比较的,这个是不能改进的,主要是可以降低比较趟数
    • 外层循环主串S不会退,只回退模式串P,并且模式串P回退的时候充分利用真前缀和真后缀的最大匹配的长度!

话不多说,大家可以看上面知乎的讲解就可以啦!

KMP算法python 模版

模版解决的问题:在主串s中查找模式串p,返回所有成功匹配的位置

python 复制代码
def kmp(s: str, p: str) -> List[int]:
    m = len(p)
    # next[i] 表示p[0] 到 p[i] 的真前缀和真后缀的最大匹配长度
    next = [0] * m
    # cnt 用于记录当前模式串p的真前缀和真后缀的最大匹配长度
    cnt = 0
    for i in range(1, m):
        b = p[i]
        while cnt and p[cnt] != b:
            cnt = pi[cnt - 1]
        if p[cnt] == b:
            cnt += 1
        next[i] = cnt
	
	# 记录答案
    pos = []
    # cnt 用于存储主串s和模式串p的匹配长度
    cnt = 0
    for i, b in enumerate(text):
    	# 不相等就让模式串p回退
        while cnt and p[cnt] != b:
            cnt = next[cnt - 1]
        if p[cnt] == b:
            cnt += 1
        if cnt == len(p):
            pos.append(i - m + 1)
            # 注意这个
            cnt = next[cnt - 1]
    return pos

习题

28.找出字符串中第一个匹配项的下标

28.找出字符串中第一个匹配项的下标

  • 典型的KMP算法的模版题目
python 复制代码
class Solution:
    def strStr(self, haystack: str, needle: str) -> int:
        # KMP算法
        m = len(needle)
        next = [0]*m 
        cnt = 0
        # 预处理next数组
        for i in range(1,m):
            b = needle[i]
            while cnt and needle[cnt] != b :
                cnt = next[cnt-1]
            if needle[cnt] == b:
                cnt += 1
            next[i] = cnt 
        
        # 开始匹配
        cnt = 0 
        for i,b in enumerate(haystack):
            while cnt and needle[cnt] != b:
                cnt = next[cnt-1]
            
            if needle[cnt] == b:
                cnt += 1
            
            if cnt == m:
                return i - m + 1
        
        return -1

1392.最长快乐前缀

1392.最长快乐前缀

  • 算法思路:直接使用KMP算法进行求解,最终的next[m-1]就是最大的长度
python 复制代码
class Solution:
    def longestPrefix(self, s: str) -> str:
        # 这个就是knp算法的max(next)
        m = len(s)
        next = [0]*(m)
        cnt = 0 
        ans = 0
        for i in range(1,m):
            b = s[i]
            while cnt and s[cnt] != b:
                cnt = next[cnt-1]
            if s[cnt] == b:
                cnt += 1
            next[i] = cnt
        return s[:next[m-1]] if next[m-1] > 0 else ""
相关推荐
大明者省21 小时前
WSL2 Ubuntu22.04 GPU训练环境配置指南
人工智能·算法·计算机视觉
白狐_7981 天前
408数据结构第8章:排序②——性质对比秒杀、场景选择与外部排序
java·数据结构·算法
zander2581 天前
LeetCode 84:柱状图中的最大矩形——单调栈如何确定左右边界
java·数据结构·算法
Shell运维手记1 天前
Linux 常用基础命令学习笔记
linux·运维·笔记·学习·算法·github
杨航 AI1 天前
O(n log n):线性对数原理拆解 这个是排序算法的黄金复杂度之一。
算法·排序算法
船厂电气自动化ai大模型1 天前
AI大模型与数学 第32课 函数凹凸性与二阶导数:拐点求解、凹凸区间计算(10道二阶导数计算题)
数据结构·人工智能·python·深度学习·算法
旖旎夜光1 天前
LeetCode 3:无重复字符的最长子串(滑动窗口) —— 题解
数据结构·c++·算法·leetcode·滑动窗口
叠层归一研究院1 天前
AGI 系统(十一):二阶网络 — 二阶递归 × 多主体 (元符号网络)
开发语言·人工智能·算法·php·agi
zlinear数据采集卡1 天前
D223的PWM电机控制:6路独立脉冲+加减速算法深度解析
arm开发·stm32·嵌入式硬件·算法·fpga开发·架构
杨石兴1 天前
31、玩具MoM:用2x2矩阵串起全套流程
人工智能·算法·矩阵·电磁学