题目说明:

今日的一些高阶程式语言对于字串的处理支援越来越强大(例如Java、C#、Perl等),不过字串搜寻本身仍是个值得探讨的课题,在这边以Boyer- Moore法来说明如何进行字串说明,这个方法快且原理简洁易懂。

题目解析:

串搜寻本身不难,使用暴力法也可以求解,但如何快速搜寻字串就不简单了,传统的字串搜寻是从关键字与字串的开头开始比对,例如 Knuth-Morris-Pratt 演算法 字串搜寻,这个方法也不错,不过要花时间在公式计算上;Boyer-Moore字串核对改由关键字的后面开始核对字串,并制作前进表,如果比对不符合则依前进表中的值前进至下一个核对处,假设是p好了,然后比对字串中p-n+1至p的值是否与关键字相同。

如果关键字中有重复出现的字元,则前进值就会有两个以上的值,此时则取前进值较小的值,如此就不会跳过可能的位置,例如texture这个关键字,t的前 进值应该取后面的3而不是取前面的7。

程序代码:

#include<iostream>
#include<string.h> using namespace std; int SkipTbl[256]; void BuildSkipTable(char* input)
{
int length = strlen(input);
for (int i=0; i < 256; ++i)
{
SkipTbl[i] = length;
} for (int i=0; i < length - 1; ++i)
{
SkipTbl[input[i]] = length - i - 1;
}
} int Search(int pos, char* input, char* key)
{
int n = strlen(input);
int m = strlen(key); while (pos < n)
{
if (memcmp(input+pos-m+1, key, m)==0)
{
return pos - m + 1;
} pos += SkipTbl[input[pos]];
} return -1;
} int main()
{
char input[100] = {0};
char key[10] = {0};
cin.getline(input, 100);
cin.getline(key, 10); int m = strlen(key);
BuildSkipTable(key); int pos = Search(m-1, input, key);
while (-1 != pos)
{
cout << "Search, index=" << pos <<endl;
pos = Search(pos+m+1, input, key);
} return 0;
}

[经典算法] 字符串搜索Boyer-Moore的更多相关文章

  1. ACM字符串处理算法经典:字符串搜索

    语法:result=strfind(char str[],char key[]); 参数: str[]:在这个源字符串查找操作 key[]:搜索字符串.不能为空字符串 回报值:     假设查找成功. ...

  2. 【ToolGood.Words】之【StringSearch】字符串搜索——基于BFS算法

    字符串搜索中,BFS算法很巧妙,个人认为BFS算法效率是最高的. [StringSearch]就是根据BFS算法并优化. 使用方法: string s = "中国|国人|zg人|fuck|a ...

  3. 记录几个经典的字符串hash算法

    记录几个经典的字符串hash算法,方便以后查看: 推荐一篇文章: http://www.partow.net/programming/hashfunctions/# (1)暴雪字符串hash #inc ...

  4. LeetCode初级算法--字符串01:反转字符串

    LeetCode初级算法--字符串01:反转字符串 搜索微信公众号:'AI-ming3526'或者'计算机视觉这件小事' 获取更多算法.机器学习干货 csdn:https://blog.csdn.ne ...

  5. LeetCode初级算法--字符串02:字符串中的第一个唯一字符

    LeetCode初级算法--字符串02:字符串中的第一个唯一字符 搜索微信公众号:'AI-ming3526'或者'计算机视觉这件小事' 获取更多算法.机器学习干货 csdn:https://blog. ...

  6. javascript常用经典算法实例详解

    javascript常用经典算法实例详解 这篇文章主要介绍了javascript常用算法,结合实例形式较为详细的分析总结了JavaScript中常见的各种排序算法以及堆.栈.链表等数据结构的相关实现与 ...

  7. JAVA经典算法40题及解答

    JAVA经典算法40题 [程序1]   题目:古典问题:有一对兔子,从出生后第3个月起每个月都生一对兔子,小兔子长到第四个月后每个月又生一对兔子,假如兔子都不死,问每个月的兔子总数为多少? 1.程序分 ...

  8. Java经典算法四十例编程详解+程序实例

    JAVA经典算法40例 [程序1]   题目:古典问题:有一对兔子,从出生后第3个月起每个月都生一对兔子,小兔子长到第四个月后每个月又生一对兔子,假如兔子都不死,问每个月的兔子总数为多少?   1.程 ...

  9. 经典算法题每日演练——第十七题 Dijkstra算法

    原文:经典算法题每日演练--第十七题 Dijkstra算法 或许在生活中,经常会碰到针对某一个问题,在众多的限制条件下,如何去寻找一个最优解?可能大家想到了很多诸如“线性规划”,“动态规划” 这些经典 ...

随机推荐

  1. flask中的request对象方法

    'accept_charsets','accept_encodings','accept_languages','accept_mimetypes','access_route','applicati ...

  2. centos 安装redis php

    $ wget http://download.redis.io/releases/redis-3.0.7.tar.gz $ tar xzf redis-3.0.7.tar.gz $ cd redis- ...

  3. enumerate

    enumerate 函数用于遍历序列中的元素并分配一个序号(序号默认从零开始 可以制定任意值): >>> for i,j in enumerate(('a','b','c')): p ...

  4. oracle学习 五 使用存储过程创建一个重置密码为123456的功能(持续更新中)

    首先写一个函数是MD5的方法 create FUNCTION GET_MD5 ( p_str in varchar2) RETURN varchar2 IS BEGIN RETURN Utl_Raw. ...

  5. java复制File文件操作

    ==========================复制File操作========================= /**  *   * @param newPath要赋值的路径  * @para ...

  6. as [Frame]元标签

    [Frame(factoryClass="XXX_Class")] 利用Frame元标签.在主SWF类名上面添加 [Frame(factoryClass="加载类类名&q ...

  7. 深入理解DLL文件

    1.LIB与DLL文件的区别 DLL是一个完整的程序,称为“动态链接库”,DLL中包含的主要有三块内容:1.全部变量 2.函数接口 3.资源:DLL中有一个函数导出表,其中每一项都是一个函数名称.通过 ...

  8. Uva 10167 - Birthday Cake 暴力枚举 随机

      Problem G. Birthday Cake Background Lucy and Lily are twins. Today is their birthday. Mother buys ...

  9. FluentData官方文档翻译

    开始 要求 .NET 4.0. 支持的数据库 MS SQL Server using the native .NET driver. MS SQL Azure using the native .NE ...

  10. HDU 1695 GCD 容斥

    GCD 题目连接: http://acm.hdu.edu.cn/showproblem.php?pid=1695 Description Given 5 integers: a, b, c, d, k ...