KMP算法的Java实现例子以及测试分析

Java实现KMP算法 直接上算法实现及测试代码 public class KMP { public static int getIndexOf(String s1, String s2) { if (s1 == null || s2 == null || s2.isEmpty() || s1.length() < s2.length()) { return -1; } char[] str1 = s1.toCharArray(); 阅读详情

 背景简介:KMP算法用来处理字符串匹配的。给你A,B两个字符串,检查B串是否是A串的子串,类似于Java的String.indexOf("")。之所以叫做KMP,是因为这个算法是由Knuth、Morris、Pratt三个提出来的,取了这三个人的名字的头一个字母。

原理介绍:找到匹配失败时的最合适的回退位置,而不是简单的回退到子串的第一个字符(常规的枚举查找方式,是简单的回退到子串的第一个字符,接下来准备写一篇KMP算法的性能分析Java实现实例),即可提高查找的效率。因此为了找到这个合适的位置,先对子串预处理,从而得到一个回退位置的数组。过多的理论就不介绍了。

总体而言比较简单,KMP算一个经典的算法例子,很多笔试、面试也会问起。现总结一下,放在这里供大家参考、交流,希望对大家有所帮助,下面直接给出实现例子,测试与分析也包含其中。

一、一个文件源代码

KMP.java

 

源代码为:

package algorithm.kmp;

/**
 * KMP算法的Java实现例子与测试、分析
 * @author 崔卫兵
 * @date 2009-3-25
 */
public class KMP {
 /**
  * 对子串加以预处理,从而找到匹配失败时子串回退的位置
  * 找到匹配失败时的最合适的回退位置,而不是回退到子串的第一个字符,即可提高查找的效率
  * 因此为了找到这个合适的位置,先对子串预处理,从而得到一个回退位置的数组
  * @param B,待查找子串的char数组
  * @return
  */
 public static int[] preProcess(char [] B) {
  int size = B.length;
  int[] P = new int[size];
  P[0]=0;
  int j=0;
  //每循环一次,就会找到一个回退位置
  for(int i=1;i<size;i++){
   //当找到第一个匹配的字符时,即j>0时才会执行这个循环
   //或者说p2中的j++会在p1之前执行(限于第一次执行的条件下)
   //p1
   while(j>0 && B[j]!=B[i]){
    j=P[j];
   }
   //p2,由此可以看出,只有当子串中含有重复字符时,回退的位置才会被优化
   if(B[j]==B[i]){
    j++;
   }
   //找到一个回退位置j,把其放入P[i]中
   P[i]=j;
  }
  return P;
 }
 
 /**
  * KMP实现
  * @param parStr
  * @param subStr
  * @return
  */
 public static void kmp(String parStr, String subStr) {
  int subSize = subStr.length();
  int parSize = parStr.length();
  char[] B = subStr.toCharArray();
  char[] A = parStr.toCharArray();
  int[] P = preProcess(B);
  int j=0;
  int k =0;
  for(int i=0;i<parSize;i++){
   //当找到第一个匹配的字符时,即j>0时才会执行这个循环
   //或者说p2中的j++会在p1之前执行(限于第一次执行的条件下)
   //p1
   while(j>0 && B[j]!=A[i]){
    //找到合适的回退位置
    j=P[j-1];
   }
   //p2 找到一个匹配的字符
   if(B[j]==A[i]){
    j++;
   }
   //输出匹配结果,并且让比较继续下去
   if(j==subSize){
    j=P[j-1];
    k++;
    System.out.printf("Find subString '%s' at %d/n",subStr,i-subSize+1);
   }
  }
  System.out.printf("Totally found %d times for '%s'./n/n",k,subStr);
 }
 
 public static void main(String[] args) {
  //回退位置数组为P[0, 0, 0, 0, 0, 0]
  kmp("abcdeg, abcdeh, abcdef!这个会匹配1次","abcdef");
  //回退位置数组为P[0, 0, 1, 2, 3, 4]
  kmp("Test ititi ititit! Test ititit!这个会匹配2次","ititit");
  //回退位置数组为P[0, 0, 0]
  kmp("测试汉字的匹配,崔卫兵。这个会匹配1次","崔卫兵");
  //回退位置数组为P[0, 0, 0, 1, 2, 3, 4, 5, 6]
  kmp("这个会匹配0次","it1it1it1");
 }
}

二、输出结果

Find subString 'abcdef' at 16
Totally found 1 times for 'abcdef'.

Find subString 'ititit' at 11
Find subString 'ititit' at 24
Totally found 2 times for 'ititit'.

Find subString '崔卫兵' at 8
Totally found 1 times for '崔卫兵'.

Totally found 0 times for 'it1it1it1'.

三、总结

总体而言,KMP算法通过找到合适的回退位置从而可以提高匹配效率,但是如果匹配位置都是第一个字符呢?例如测试代码中的

//回退位置数组为P[0, 0, 0, 0, 0, 0]
kmp("abcdeg, abcdeh, abcdef!这个会匹配2次","abcdef");

接下来准备写一篇KMP算法的性能分析Java实现实例,下文再见。^_^

BF、KMP与BM测试用数据 刁肥宅制作的,BF、KMP与BM测试用数据,是由大小写字母与数字组成的随机字符串,数量级为10到10^9。 立即下载

相关推荐

利用正射影像对斜射图像进行反向投影

因此,RANSAC算法可以通过计算inliners和outliers的数量来评估估计关键点的质量,确保与其他点不一致的点不会在Homography矩阵中被估计。然后,它通过考虑关键点周围区域中图像的梯度大小和方向来计算每个提取的关键点的方向。由于单应性矩阵的计算可能会受到两个图像中异常值的存在的影响,这将导致矩阵的不正确估计并导致沿图像的对准和映射不良。FLANN匹配器的方法基于K近邻搜索的概念,即从图像中找到k个近邻。找到相机在正射影像坐标系中的位置并在正射影像上绘制重叠区域的边界框。

gis收藏家的博客 1511

数据结构与算法~串的模式匹配~KMP匹配算法中next值的C语言源代码和测试数据

next值的C语言源代码 #include<stdlib.h> #include<stdio.h> #define MAX 20 typedef struct { char *ch; int length; }heapstring; /*生成一个串*/ void Str_Assign(heapstring *s){ if (!(s->ch=(cha...

cskmyjy的博客 1528

VSAN闪存缓存磁盘故障处理指南-RAID0模式实战解析

本文详细解析了VSAN集群中RAID0模式下的闪存缓存磁盘故障处理全流程。通过模拟真实故障场景,从告警识别、数据重建策略到磁盘组重构,提供了手把手的实战操作指南,并深入探讨了RAID0缓存故障的独特影响与风险,为运维人员应对此类高性能存储架构的突发问题提供了专业解决方案。

assembly8low的博客 444

KMP匹配算法-效率测试

总结: KMP匹配无规律的匹配字符串效果不太好。 KMP匹配有关联的字符串效率比较高。 KMP匹配无关数据,效率也许比简单匹配低。 无关数据匹配//无关数据匹配 //模式匹配字符串P A B C D A B D A B A C D -1 0 0 0 -1 0 2 -1 0 2 1 0 //文本串S E H

《我是你的正能量》 2895

避坑指南:微信小程序蓝牙广播在iOS上的那些‘坑’(附serviceUuids传值解决方案)

本文深入解析微信小程序蓝牙广播在iOS平台上的开发难点,特别是`serviceUuids`传值解决方案。通过对比iOS与安卓的蓝牙协议实现差异,提供实战编码策略和硬件端配合方案,帮助开发者有效规避兼容性问题,提升蓝牙外围设备开发效率。

weixin_30316097的博客 423

【谷粒商城】分布式事务与下单

=购物车== 构建gulimall-cart,复制静态资源到nginx,修改网关 购物车分为离线购物车和登录购物车 离线购物车重启浏览器了也还有 1、购物车需求 特点:读多写少,放入数据库并不合适 登录状态:登录购物车 放入数据库 mongodb 放入redis(采用) 登录以后,将离线购物车里合并后清空离线购物车 未登录状态:离线购物车 放入localstorage浏览器的技术 cookie WebSQL 放入redis(采用) 浏览器重启后还在 2、购物车VO (1) 数据结构分析

努力充实,远方可期 1万+

KMP 算法详解

KMP 算法(Knuth-Morris-Pratt 算法)是一个著名的字符串匹配算法,效率很高,但是确实有点复杂。 很多读者抱怨 KMP 算法无法理解,这很正常,想到大学教材上关于 KMP 算法的讲解,也不知道有多少未来的 Knuth、Morris、Pratt 被提前劝退了。有一些优秀的同学通过手推 KMP 算法的过程来辅助理解该算法,这是一种办法,不过本文要从逻辑层面帮助读者理解算法的原理。十行...

fdl123456的博客 832

金蝶个版本下载地址,记得保存收藏。

专业版 V10.0 http://downloads.cmcloud.cn/kis/kis_pro/10.0/kiszybV10sp1.rar V11.0 http://downloads.cmcloud.cn/kis/kis_pro/11.0/KISV11Setup.rar V12.0 http://dow...

饺子的博客 2503

【数据结构】KMP算法(详解)

KMP算法+acwing

honortech的博客 8256

Ubuntu零基础入门到精通【1.2讲】:Ubuntu 与 Linux 的关系 —— 你用的到底是什么?

🏆 本文收录于 《滚雪球学 Ubuntu》 专栏。 本专栏面向有一定计算机基础,但尚未系统学习 Linux / Ubuntu 的读者,采用“滚雪球式学习法”:先装好、再会用、再理解、再优化、再实战,带你从第一次进入 Ubuntu 桌面 / 终端开始,逐步掌握 Ubuntu 的日常使用、命令操作、软件安装、系统配置、开发环境搭建与服务器部署能力。

**My Coding Family** 3116

极智嘉嵌入式面试题及参考答案

IIC(Inter-Integrated Circuit)即集成电路总线,是一种由 PHILIPS 公司开发的两线式串行总线,用于连接微控制器及其外围设备。它仅使用两根线,即串行数据线 SDA 和串行时钟线 SCL,就能实现多个设备之间的通信,具有简单、高效、占用资源少等优点,广泛应用于各种嵌入式系统中。

大模型大数据攻城狮的专栏 921

数据结构之KMP算法:彻底搞懂kmp算法

数据结构的学习,kmp匹配算法困扰我许久,此处来一个总结(仅供自己复习了解参考使用),如果有不对的地方请多多指点。好了废话不多说我们直接开始好吧。首先我想再次之前先讲述一下暴力匹配解法去匹配。

梁小布的博客 1431

复分析 阿尔福斯(Ahlfors) 第三版答案 英文

答案分为十章,有部分习题没有答案,全英文复分析阿尔福斯(Ahlfors) 第三版答案

java实现kmp_KMP算法的Java实现例子以及测试分析

背景简介:KMP算法用来处理字符串匹配的。给你A,B两个字符串,检查B串是否是A串的子串,类似于Java的String.indexOf("")。之所以叫做KMP,是因为这个算法是由Knuth、Morris、Pratt三个提出来的,取了这三个人的名字的头一个字母。原理介绍:找到匹配失败时的最合适的回退位置,而不是简单的回退到子串的第一个字符(常规的枚举查找方式,是简单的回退到子串的第一个字符,接下来...

weixin_29107289的博客 480

IEM模型,地表粗糙度模拟

利用微波反演土壤水分时候,利用IEM模型可以实现对随机地表的模拟

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

KMP与枚举算法的实现例子以及性能分析(Java)

在上一篇《KMP算法的Java实现例子以及测试分析》中已经介绍了KMP概念以及原理,这一篇中结合枚举字符串算法比较一下两者的性能,并且给出了KMP、枚举算法的Java实现,以及测试代码与结果,放在这里供大家参考、交流,希望对大家有所帮助。KMP算法的优势主要有两点:1,无回溯,即对于主串的循环是线性的,也就是说,一直朝前招,指针是递增的,而不会回退;2,对子串加以预处理,从而找到匹配失败时子串

兰苹果 1995

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

KMP算法中next函数的java实现

KMP算法中next函数的java实现

AI吃葡萄干的专栏 2529

KMP算法详解及Java实现

KMP算法详解及Java实现KMP算法描述部分匹配算法原理部分匹配算法实现(Java)KMP匹配算法Java实现 以前在学习计算机数据结构时,涉及到基础算法KMP算法,学习了好几次,在网上找了很多资料,说得也不是清楚,后来在看了阮一峰老师的博客后,终于理解了。 KMP算法描述 说起KMP算法,就不得不说字符串匹配,最初的字符串匹配效率并不高,但是为了解决提高字符串匹配效率,Knuth-Mor...

banche163的专栏 1035

java实现kmp_KMP算法java实现

一、KMP算法在数据结构,字符串的操作中,有一个非常重要的方法,即在一个字符串中(主串)搜索一个特定的字符串(子串或模式串),若找到则返回字符串的位置,未找到则返回-1;最简单的方法则是采用回溯的方法,又叫Brute-Force算法,即从头遍历主串,若与子串第一个字符一样则比对第二个字符串,若不相同则回溯到第一个字符的下一个字符开始重新比较。设主串为fffff….ffff模式串为fffff…ff...

weixin_30305727的博客 693

【数据结构与算法】KMP算法

KMP算法

南瓜籽_的博客 910

js实现kmp算法_kmp算法java实现并计算实现速度

kmp算法java实现并计算实现速度1、普通的字符匹配没有什么奇效2、牛逼的算法都是用在特殊的地方package com.ccc;public class Test {public static void main(String arg[]) {//毫秒 System.currentTimeMillis()//纳秒 System.nanoTime()long start1 = System.nan...

weixin_35790607的博客 226

算法:用Java实现用KMP算法来进行字符串的匹配

KMP算法是一种改进的字符串匹配算法,由D.E.Knuth,J.H.Morris和V.R.Pratt提出的,因此人们称它为克努特—莫里斯—普拉特操作(简称KMP算法)。KMP算法的核心是利用匹配失败后的信息,尽量减少模式串与内容串的匹配次数以达到快速匹配的目的。具体实现就是通过一个next[]数组来实现,next[]数组本身包含了模式串的局部匹配信息。KMP算法的时间复杂度O(m+n)。 下面是我用Java实现的KMP字符串匹配算法:KMP.java类

weixin_39448458的博客 597

KMP java实现 实测KMP与indexOf速度

java库的代码是暴力解的,可是库的indexOf要比KMP快上百倍emmmmmm 以下是code package KMP; public class Main { //实测 KMP 与 indexOf public static void main(String[] args) { String str = "hdgzfsdgzszgfdzgvrvdfzgabcabcababa...

changaspl 1661

算法 字符串匹配之朴素算法和KMP算法及JAVA代码实现

暴力匹配算法假设现在我们面临这样一个问题:有一个文本串S,和一个模式串P,现在要查找P在S中的位置,怎么查找呢?如果用暴力匹配的思路,并假设现在文本串S匹配到 i 位置,模式串P匹配到 j 位置,则有: 如果当前字符匹配成功(即S[i] == P[j]),则i++,j++,继续匹配下一个字符; 如果失配(即S[i]! = P[j]),令i = i - (j - 1),j = 0。相当于每次匹配失败时

Heqianqian的博客 2608

算法设计与分析(Java实现)—— KMP 算法

算法设计与分析(Java实现)—— KMP 算法

海绵猿宝的博客 300

KMP算法Java实现

KMP算法JAVA实现

weixin_43978420的博客 418

算法笔记(一)——KMP算法

1. 暴力匹配(BF)算法 基本概念 BF算法,即暴力(Brute Force)算法,是普通的模式匹配算法,BF算法的思想就是将目标串S的第一个字符与模式串的第一个字符进行匹配,若相等,则继续比较S的第二个字符和 T的第二个字符;若不相等,则比较S的第二个字符T的第一个字符,依次比较下去,直到得出最后的匹配结果。BF算法是一种蛮力算法。 分析BF算法 光看定义晦涩难懂,接下来我将举例子与大家一起学习: 假定我们给出字符串"ababcabcdabcde"做为主串,然后给出子串"abcd",现..

m0_58367586的博客 1615
上一篇: JSP中Forward与Redirect的区别(用例子说明)
下一篇: KMP与枚举算法的实现例子以及性能分析(Java)
cuiweibing
博客等级 码龄22年 23粉丝 28原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值