Theory: Search in a string(理论:在字符串中搜索)

处理数据时的一项基本技能是能够搜索它并找到特定的信息位。在 Python 中处理文本数据时,您可能需要获取有关其内容的一些信息:它是否包含特定的子字符串(即字符串的一部分)、该子字符串在哪里,或者它在文本中出现的次数。在本主题中,我们将学习如何做到这一点。

子串搜索算法

我们将从子字符串搜索问题开始。给定两个字符串,textpattern ,我们需要确定在text中是否至少出现了一次pattern。解决这个问题最简单、最自然的方法是依次考虑文本中长度等于模式长度的所有子字符串,并将它们与模式本身进行比较。如果至少在一种情况下所有对应的符号都匹配,则找到该模式。如果这些尝试都没有成功,我们应该指出没有模式在文本中。下面是如何在 Python 中实现这个简单的算法:

def contains(text, pattern):
    for i in range(len(text) - len(pattern) + 1):
        found = True

        for j in range(len(pattern)):
            if text[i + j] != pattern[j]:
                found = False
                break

        if found:
            return True

    return False

命名的函数contains将两个字符串textpattern, 作为输入,如果text包含pattern,则返回True,否则返回False

在外循环的每一步for,我们创建一个名为found的变量并赋值为True. 然后,在内部for循环中,我们开始比较pattern与当前的子字符串text。如果至少有一个对应的符号不匹配,我们将变量设置foundFalse并中断内部循环。内部for循环完成后,我们检查found变量的状态。如果仍然存在True,则表示 的每个符号都pattern与当前子字符串匹配。在这种情况下,我们返回True表明pattern已找到。否则,我们进入下一次迭代并开始考虑下一个子字符串。如果没有一个比较成功,即外部for循环完成所有迭代,函数返回False指示pattern未找到。

以下是如何使用此算法:

contains("abacabad", "cab")  # True
contains("abacabad", "abacabad")  # True
contains("aba", "")  # True
contains("abacabad", "hello")  # False

现在我们知道有一个子字符串搜索算法以及如何在 Python 中实现它。但是,也有解决问题的内置函数和运算符。让我们看看它们是什么。

成员检测

另一种定义字符串中是否存在特定模式的方法称为成员资格测试,它是在运算符in和的帮助下实现的not in。当我们写pattern in string时,左操作数应该是一个字符串,并且成员资格测试检查是否string包含pattern作为子字符串。

如果成员资格测试返回True,这意味着存在一个string起始位置,您可以从该位置读取字符串中的模式。

print("apple" in "pineapple")  # True
print("milk" in "yogurt")      # False

有趣的是,空字符串被认为是任何字符串的子字符串。

print('' in '')           # True
print('' not in "lemon")  # False

字符串中的布尔搜索

除了知道子字符串只出现在字符串中之外,我们还可以确定字符串以特定模式开始结束。startswith() 和 endswith()方法

email = "email_address@something.com"
print(email.startswith("www."))          # False
print(email.endswith("@something.com"))  # True

可选值startend可添加绑定的搜索区域:string.startswith(pattern, start, end)。当我们只指定一个附加元素时,它会自动被视为start.

email = "my_email@something.com"
print(email.startswith("email", 2))  # False
print(email.startswith("email", 3))  # True

在上面的示例中,当我们将start参数指定为2时,我们将搜索限制为子字符串"_email@something.com",它实际上不是以 开头"email"然后我们通过将 start 设置为3来修复这个错误。

请注意,由开始索引和结束索引绑定的子字符串确实包括具有开始索引的字符,但包括具有结束索引的元素。

email = "my_email@something.com"
print(email.endswith("@", 5, 8))  # False
print(email.endswith("@", 5, 9))  # True

在第一种情况下为搜索定义的子字符串是"ail",而在第二种情况下是"ail@"

元素位置

现在,我们知道如何检查字符串是否包含子字符串、以它开头或结尾,让我们学习如何定义子字符串的确切位置。我们可以使用方法find()index()这样做:

best = "friend"

print(best.find("i"))   # 2
print(best.index("i"))  # 2

它们的工作原理完全相同,只是前者-1在找不到给定元素时返回,而后者则 raise ValueError

print(best.find("u"))   # -1
print(best.index("u"))  # ValueError

因此,find()下面的所有示例也可以使用index()

我们既可以搜索单个字符,也可以搜索更长的子字符串。在后一种情况下,返回子字符串的第一个字符的索引。

print(best.find("end"))  # 3

在字符串friend中,子字符串end占据35的位置,并返回起始索引。请记住,这两种方法都只返回我们搜索的元素第一次出现的索引。

magic = "abracadabra"
print(magic.find("ra"))  # 2

但是,我们可以另外指定搜索的间隔,就像布尔搜索一样:string.find(pattern, start, end)

print(magic.find("ra"5))      # 9
print(magic.find("ra"510))  # -1

再一次,结束索引不包括在搜索区域中。

或者,我们可以使用方法rfind()rindex()从字符串的末尾向后搜索。

print(magic.rfind("ra"))  # 9
print(magic.rindex("a"))  # 10

元素数量

最后,计算一个元素(字符或子字符串)在字符串中出现的次数通常很有用,为此,我们可以使用方法count().

magic = "abracadabra"

print(magic.count("abra"))  # 2
print(magic.count("a"))     # 5

概括

在本主题中,我们研究了搜索字符串的不同方面,并学习了如何定位特定模式。现在您将能够:

  • 要在 Python 中实现子字符串搜索算法,
  • 要测试文本中的成员资格,
  • 要检查字符串是否以特定模式开始或结束,
  • 要找到子字符串的确切位置,
  • 计算一个模式在文本中出现的次数。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值