Boyer–Moore (BM)字符串搜索算法
在计算机科学里,Boyer-Moore字符串搜索算法是一种非常高效的字符串搜索算法。它由Bob Boyer和J Strother Moore设计于1977年。此算法仅对搜索目标字符串(关键字)进行预处理,而非被搜索的字符串。虽然Boyer-Moore算法的执行时间同样线性依赖于被搜索字符串的大小,但是通常仅为其它算法的一小部分:它不需要对被搜索的字符串中的字符进行逐一比较,而会跳过其中某些部分。通常搜索关键字越长,算法速度越快。它的效率来自于这样的事实:对于每一次失败的匹配尝试,算法都能够使用这些信息来排除尽可能多的无法匹配的位置。
假设被检索文字列是“1234567890”,检索文字列是“MOORE”。简单的比较需要执行十次才得到结论不匹配。
被检索文字列:1234567890
第一次比较:M.... (M和1比较,不匹配)
第二次比较: M.... (M和2比较,不匹配)
第三次比较: M.... (M和3比较,不匹配)
...
第十次比较: M....(M和0比较,不匹配)
※未参与比较的文字用【.】占位。
BM算法只需要2次比较。
被检索文字列:1234567890
第一次比较:....E (E和5比较,不匹配,并且5不是MOORE中任何文字)
第二次比较: ....E (E和0比较,不匹配,并且0不是MOORE中任何文字)
第一次从检索文字的末尾开始,因为如果被检索文字的第5文字位置不是E,则无论前4个文字是什么,都绝不可能匹配了。这一点比较容易理解。
那么,为什么不用E和6比较呢?
这是BM算法又一处精妙之处。在E和5进行比较的时候不仅知道他们不相等,而且还知道了5不和检索文字MOORE中的任何一个文字相等,这使得下面这些比较都可以省略掉。
被检索文字列:....5......
不需要的比较: ...R. (E和5比较时也同时发现5不等于R,于是这个比较是不必要的)
不需要的比较: ..O.. (E和5比较时也同时发现5不等于O,于是这个比较是不必要的)
不需要的比较: .O... (E和5比较时也同时发现5不等于O,于是这个比较是不必要的)
不需要的比较: M.... (E和5比较时也同时发现5不等于M,于是这个比较是不必要的) 发明者论文:
http://www.cs.utexas.edu/users/moore/publications/fstrpos.pdf
http://www.cs.utexas.edu/~moore/best-ideas/string-searching/fstrpos-example.html
BM算法是跳跃着前进的。
第三步:BM过程展示
BM算法实施方法是从后向前进行匹配。我们先来见证一下这种方法的威力。

此处采用作者论文中的例子:
从模式串最后一个字符开始匹配,发现F和T不匹配,除此之外,F在模式串AT-THAT中根本就不存在,这个意味着匹配的可能性为0.我们可以直接跳过前7个字符。

我们只是添加了一个判断,效率瞬间提高很多。这个和BF、KMP有什么不同呢?这两种算法,目标串的指针i总是以一步一步的前进,而BM则并没有采用这种方式,它可以一下子增加7(本例),这就是跳跃式思维的表现形式,这个更接近人的思维方式。(下面会有更深入层次的分析前缀匹配和后缀的匹配差异)
BM算法采用了两种启发性的规则:坏字符规则和好后缀规则,决定跳跃的距离。
1) 坏字符规则(Bad Character)
在BM算法从后向前扫描的过程中,若已经有m个字符匹配成功,第m+1个字符X(从后向前)匹配失败,则按下面两种情况讨论:
a)如果字符x在模式P中没有出现,直接全部跳过该区域。
b)如果字符x在模式P中出现,则以该字符进行对齐。

我们其实已经见识过a)这个规则,就是上面的例子。
2)好后缀规则(Good Suffix)
在BM算法从后向前扫描的过程中,若已经有m个字符匹配成功,第m+1个字符X(从后向前)匹配失败,则按下面两种情况讨论:
a) 如果已经匹配的m个字符,在模式串其他位置也出现过记为m’,则将m’和这m个字符对齐。

b) 如果a)中所说情况没有出现,此时需要检查模式串P,若P存在最长前缀s 同时也是P的后缀,则将s和P对应的后缀对齐。

上述两个好后缀规则中取最小的一个移动。
其实,在好后缀规则中,如果第一条成立其实就不用检查第二条,因为第二条如果存在,移动距离肯定比第一条大。但是如果第一条不成立,意味着移动距离是模式串P的长度,此时需要检查第二条,如果第二条成立,则安全移动的距离便变小了。
更多:
http://wlh0706-163-com.iteye.com/blog/1847214
http://dsqiu.iteye.com/blog/1700312
http://wlh0706-163-com.iteye.com/blog/1847214
http://blog.csdn.net/left_la/article/details/8881311
Boyer–Moore (BM)字符串搜索算法的更多相关文章
- BF + KMP + BM 字符串搜索算法
BF #include <stdio.h> #include <string.h> int simplicity(char *s, char *t, int pos); int ...
- grep之字符串搜索算法Boyer-Moore由浅入深(比KMP快3-5倍)
这篇长文历时近两天终于完成了,前两天帮网站翻译一篇文章“为什么GNU grep如此之快?”,里面提及到grep速度快的一个重要原因是使用了Boyer-Moore算法作为字符串搜索算法,兴趣之下就想了解 ...
- grep之字符串搜索算法Boyer-Moore由浅入深(比KMP快3-5倍)(转)
这篇长文历时近两天终于完成了,前两天帮网站翻译一篇文章“为什么GNU grep如此之快?”,里面提及到grep速度快的一个重要原因是使用了Boyer-Moore算法作为字符串搜索算法,兴趣之下就想了解 ...
- 从入门到精通之Boyer-Moore字符串搜索算法详解
本文讲述的是Boyer-Moore算法,Boyer-Moore算法作为字符串搜索算法,兴趣之下就想了解这个算法,发现这个算法一开始还挺难理解的,也许是我理解能力不是很好吧,花了小半天才看懂,看懂了过后 ...
- 字符串搜索算法Boyer-Moore
整理日: 2015年2月16日 1. 主要特征 假设文本串text长度为n,模式串pattern长度为m,BM算法的主要特征为: 从右往左进行比较匹配(一般的字符串搜索算法如KMP都是从从左往右进行匹 ...
- Boyer Moore算法(字符串匹配)
上一篇文章,我介绍了KMP算法. 但是,它并不是效率最高的算法,实际采用并不多.各种文本编辑器的"查找"功能(Ctrl+F),大多采用Boyer-Moore算法. Boyer-Mo ...
- Leetcode OJ : Implement strStr() [ Boyer–Moore string search algorithm ] python solution
class Solution { public: int strStr(char *haystack, char *needle) { , skip[]; char *str = haystack, ...
- 字符串核对之Boyer-Moore算法
算法说明: 在计算机科学里,Boyer-Moore字符串搜索算法是一种非常高效的字符串搜索算法.它由Bob Boyer和J Strother Moore设计于1977年.此算法仅对搜索目标字符串(关键 ...
- Boyer-Moore 字符串匹配算法
字符串匹配问题的形式定义: 文本(Text)是一个长度为 n 的数组 T[1..n]: 模式(Pattern)是一个长度为 m 且 m≤n 的数组 P[1..m]: T 和 P 中的元素都属于有限的字 ...
随机推荐
- 用VIM删除空行
从网上找了一个 :g/^s*$/d 开始用的挺好,后来遇到一种空格开头的空行,就不好用了. MSDN上说正则匹配空行用/^\s*$/,就试着把上面的命令改为: :g/^\s*$/d 就可以了. 用的操 ...
- 成功的背后!(给所有IT人)----转载:来自CSDN第一名博主
转载:来自CSDN第一名博主:http://blog.csdn.net/phphot/article/details/2187505 放在这里激励你我! 正文: 成功的背后,有着许多不为人知的故事,而 ...
- Convert Sorted List to Balanced Binary Search Tree (BST)
(http://leetcode.com/2010/11/convert-sorted-list-to-balanced-binary.html) Given a singly linked list ...
- 尼康D5100使用设置及技巧,同样也适用尼康D5200
尼康D5100使用设置及技巧,同样也适用尼康D5200,希望对新手能有点帮助. 一.设置 1.优化校准:可以在menu菜单中找到它,一般使用"标准"就可以,建议将"标准& ...
- 使用 http://httpbin.org/ 验证代理地址
发现一个很方便的工具,在Linux 下使用 curl http://httpbin.org/ 可以返回当前使用的一些网络信息
- 如何在windows的DOS窗口中正常显示中文(UTF-8字符)
打开CMD.exe命令行窗口,通过 chcp命令改变代码页 UTF-8的代码页为65001,ANSI/OEM - 简体中文 GBK为936,window default OEM - 美国为437 如果 ...
- ElaticSearch网站
http://www.tuicool.com/articles/r2QJVr http://so.searchtech.pro/articles/2013/06/16/1371392427213.ht ...
- 简单测试运行时类信息(RTTI),附详细例子
新建一个单元文件,填写如下代码,然后保存为 ClassInfoUnit.pas,这里定义了一个结构,用来读取指定类的信息. unit ClassInfoUnit; interface uses Cla ...
- 让Java的反射跑快点
由于反射涉及动态解析的类型,某些Java虚拟机的优化不能被执行,所以导致了一定的性能的问题,特别是在JDK6以前特别严重,有时甚至达到数百倍,但是在JDK6以后,据说性能差别就不是哪么大了,JDK对此 ...
- BZOJ 4300 绝世好题(位运算)
[题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=4300 [题目大意] 给出一个序列a,求一个子序列b,使得&和不为0 [题解] ...