You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于Python实现反向搜索(Backward search)统计子串出现次数

嘿,我来帮你理清用反向搜索(Backward Search)结合zip遍历字符串来统计子串出现次数的具体思路,结合你给出的例子一步步拆解:

核心思路:反向搜索的优势

要统计子串ban的出现次数,反向搜索的核心是从子串的最后一个字符开始匹配——也就是先找n,再找a,最后找b。这种方式能更早排除不匹配的情况,尤其是结合排序后的字符串s1,可以快速缩小搜索范围,大幅提升效率。

具体实现步骤

1. 预处理目标子串

先把目标子串ban反转成nab,这样我们就可以从最后一个字符开始依次匹配:

target = 'ban'
rev_target = target[::-1]  # 得到 'nab'

2. 利用排序字符串s1缩小搜索范围

因为s1是s的排序版本,相同字符会集中在一起。我们可以先定位到rev_target第一个字符(也就是n)在s1中的区间,这样不用遍历整个s,只需要在这个区间内搜索即可:

original = 'panamabananas$'
s = 'smnpbnnaaaaa$a'
s1 = '$aaaaaabmnnnps'

first_char = rev_target[0]
# 找到s1中第一个'n'的位置
start_idx = s1.index(first_char)
# 找到s1中最后一个'n'的位置
end_idx = len(s1) - s1[::-1].index(first_char) - 1

3. 结合遍历(或zip)完成匹配统计

这里我们可以遍历s中缩小后的区间,同时跟踪反向子串的匹配进度:

count = 0
current_match_pos = 0  # 记录当前匹配到反向子串的第几个字符

for char in s[start_idx:end_idx+1]:
    # 如果当前字符匹配反向子串的当前位置,推进匹配进度
    if current_match_pos < len(rev_target) and char == rev_target[current_match_pos]:
        current_match_pos += 1
        # 完全匹配反向子串,说明找到一个目标子串
        if current_match_pos == len(rev_target):
            count += 1
            current_match_pos = 0  # 重置进度,继续寻找下一个匹配
    else:
        # 不匹配则重置进度,同时检查当前字符是否是反向子串的起始字符
        current_match_pos = 0
        if char == rev_target[0]:
            current_match_pos = 1

print(f"子串'{target}'的出现次数: {count}")

为什么用zip?

如果需要同时对比s和s1的字符(比如验证排序后的位置对应关系),可以用zip(s, s1)遍历,在遍历过程中同步获取原字符串和排序后的字符,辅助我们调整搜索区间:

# 示例:用zip遍历同时查看s和s1的对应字符
for s_char, s1_char in zip(s, s1):
    print(f"s中的字符: {s_char}, s1中的字符: {s1_char}")

这种方式可以让你在遍历过程中,实时参考排序后的字符分布,动态调整匹配策略。

关键优势总结

  • 反向搜索减少无效匹配:从子串末尾开始匹配,能快速排除不相关的字符,避免正向搜索中“前面匹配但后面不匹配”的无效遍历。
  • 排序字符串缩小范围:利用s1的排序特性,直接定位到可能包含目标子串末尾字符的区间,大幅减少需要遍历的字符数量。

内容的提问来源于stack exchange,提问作者Joe Smith

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 07:46:05