返回

LeetCode日常之字符串:28 实现strStr()

闲谈

对于初学算法的人来说,LeetCode题库绝对称得上编程之友。日常刷题练习,不仅可以熟悉编程语言本身的语法,还可以锻炼基本的算法逻辑思维能力,为未来的编程之路打下扎实的基础。今天,让我们把目光聚焦在LeetCode题库中第28题,一个看似简单却极具挑战性的字符串题目——实现strStr()。

问题剖析

1.明确输入和输出:

  • 输入:两个字符串haystack和needle。
  • 输出:needle字符串在haystack字符串中的第一个匹配位置,如果不存在则返回-1。

2.特殊情况处理:

  • 当needle字符串为空时,返回-1。
  • 当haystack字符串为空,且needle字符串不为空时,返回-1。

3.核心实现:

  • 找出needle字符串在haystack字符串中的第一个匹配位置。

解决思路

1.朴素匹配算法:

朴素匹配算法是最直观的解法,它从haystack字符串的第一个字符开始,依次与needle字符串的第一个字符进行比较。如果匹配成功,则继续比较haystack字符串的第二个字符与needle字符串的第二个字符,以此类推,直到needle字符串完全匹配或haystack字符串遍历结束。

2.KMP算法:

KMP算法(Knuth-Morris-Pratt)是一种改进的字符串匹配算法,它利用预处理阶段计算出的失配函数来加速匹配过程。失配函数本质上是一种状态机,它记录了needle字符串中每个字符在匹配失败时应该跳转到哪个位置,从而减少不必要的比较。

具体实现

1.朴素匹配算法实现:

def strStr(haystack, needle):
    """
    朴素匹配算法实现
    :param haystack: 主串
    :param needle: 模式串
    :return: 模式串在主串中第一次出现的位置,如果没有找到返回-1
    """
    if not needle:
        return 0
    if not haystack:
        return -1
    n, m = len(haystack), len(needle)
    for i in range(n - m + 1):
        if haystack[i:i + m] == needle:
            return i
    return -1

2.KMP算法实现:

def strStr(haystack, needle):
    """
    KMP算法实现
    :param haystack: 主串
    :param needle: 模式串
    :return: 模式串在主串中第一次出现的位置,如果没有找到返回-1
    """
    if not needle:
        return 0
    if not haystack:
        return -1
    n, m = len(haystack), len(needle)
    # 预处理失配函数
    failure = [0] * m
    j = 0
    for i in range(1, m):
        while j > 0 and needle[i] != needle[j]:
            j = failure[j - 1]
        if needle[i] == needle[j]:
            j += 1
        failure[i] = j
    # 匹配过程
    i, j = 0, 0
    while i < n:
        while j > 0 and haystack[i] != needle[j]:
            j = failure[j - 1]
        if haystack[i] == needle[j]:
            j += 1
        if j == m:
            return i - m + 1
        i += 1
    return -1

总结

LeetCode题库中的第28题要求我们实现strStr()函数,该函数用于在给定的haystack字符串中查找needle字符串的第一个匹配位置。如果needle字符串为空,则返回-1。本文从题目出发,逐层分析问题,并逐步深入探讨strStr()函数的实现思路和细节,帮助您更透彻地理解字符串匹配算法。无论是朴素匹配算法还是KMP算法,它们都各有优劣势,在不同的场景下都有其应用价值。