java 字符串子串_java实现字符串匹配求两个字符串的最大公共子串

2023-05-16

本文实例讲述了java实现求两个字符串最大公共子串的方法。分享给大家供大家参考,具体如下:

最近在项目工作中有一个关于文本对比的需求,经过这段时间的学习,总结了这篇博客内容:求两个字符串的最大公共子串。

算法思想:基于图计算两字符串的公共子串。具体算法思想参照下图:

fbd4cdeb5b4efb9a1b2948ff132b80f3.png

输入字符串S1:achmacmh    输入字符串S2:macham

第a步,是将字符串s1,s2分别按字节拆分,构成一个二维数组;

二维数组中的值如b所示,比如第一行第一列的值表示字符串s2和s1的第一个字节是否相等,若相等就是1,否则就是0,最终产生b所示的二维数组;

分别求二维数组中斜线上的公共因子(斜线为元素a右下角值,即a[i][j]的下一个元素是a[i+1][j+1];公共因子为1所在的位置构成的字符串);

对所有公共因子排序,返回最大的公共因子的值。

具体的实现代码如下所示:

package cn.lulei.compare;

import java.util.ArrayList;

import java.util.Collections;

import java.util.Comparator;

import java.util.List;

public class StringCompare {

private int a;

private int b;

public String getMaxLengthCommonString(String s1, String s2) {

if (s1 == null || s2 == null) {

return null;

}

a = s1.length();//s1长度做行

b = s2.length();//s2长度做列

if(a== 0 || b == 0) {

return "";

}

//设置匹配矩阵

boolean [][] array = new boolean[a][b];

for (int i = 0; i < a; i++) {

char c1 = s1.charAt(i);

for (int j = 0; j < b; j++) {

char c2 = s2.charAt(j);

if (c1 == c2) {

array[i][j] = true;

} else {

array[i][j] = false;

}

}

}

//求所有公因子字符串,保存信息为相对第二个字符串的起始位置和长度

List childStrings = new ArrayList();

for (int i = 0; i < a; i++) {

getMaxSort(i, 0, array, childStrings);

}

for (int i = 1; i < b; i++) {

getMaxSort(0, i, array, childStrings);

}

//排序

sort(childStrings);

if (childStrings.size() < 1) {

return "";

}

//返回最大公因子字符串

int max = childStrings.get(0).maxLength;

StringBuffer sb = new StringBuffer();

for (ChildString s: childStrings) {

if (max != s.maxLength) {

break;

}

sb.append(s2.substring(s.maxStart, s.maxStart + s.maxLength));

sb.append("\n");

}

return sb.toString();

}

//排序,倒叙

private void sort(List list) {

Collections.sort(list, new Comparator(){

public int compare(ChildString o1, ChildString o2) {

return o2.maxLength - o1.maxLength;

}

});

}

//求一条斜线上的公因子字符串

private void getMaxSort(int i, int j, boolean [][] array, List sortBean) {

int length = 0;

int start = j;

for (; i < a && j < b; i++,j++) {

if (array[i][j]) {

length++;

} else {

sortBean.add(new ChildString(length, start));

length = 0;

start = j + 1;

}

if (i == a-1 || j == b-1) {

sortBean.add(new ChildString(length, start));

}

}

}

//公因子类

class ChildString {

int maxLength;

int maxStart;

ChildString(int maxLength, int maxStart){

this.maxLength = maxLength;

this.maxStart = maxStart;

}

}

/**

* @param args

*/

public static void main(String[] args) {

// TODO Auto-generated method stub

System.out.println(new StringCompare().getMaxLengthCommonString("achmacmh", "macham"));

}

}

程序最终执行结果是:

b3ce5260b8a2a4fcd869841dfb971f58.png

对于两个文件的比对个人认为可以参照这种算法思想(自己现在并为实现),在日后的博客中将会写到。

上述实现过程中,用数组保存了所有的公共子串信息,然后排序取最大的子串,这种做法如果只是求最大子串的话,算法就不是很合理,因此做了如下修改,List只保存当前计算中最大的子串,具体实现如下:

/**

*@Description: 字符串比较

*/

package com.lulei.test;

import java.util.ArrayList;

import java.util.List;

public class StringCompare {

private int a;

private int b;

private int maxLength = -1;

public String getMaxLengthCommonString(String s1, String s2) {

if (s1 == null || s2 == null) {

return null;

}

a = s1.length();//s1长度做行

b = s2.length();//s2长度做列

if(a== 0 || b == 0) {

return "";

}

//设置匹配矩阵

boolean [][] array = new boolean[a][b];

for (int i = 0; i < a; i++) {

char c1 = s1.charAt(i);

for (int j = 0; j < b; j++) {

char c2 = s2.charAt(j);

if (c1 == c2) {

array[i][j] = true;

} else {

array[i][j] = false;

}

}

}

//求所有公因子字符串,保存信息为相对第二个字符串的起始位置和长度

List childStrings = new ArrayList();

for (int i = 0; i < a; i++) {

getMaxSort(i, 0, array, childStrings);

}

for (int i = 1; i < b; i++) {

getMaxSort(0, i, array, childStrings);

}

StringBuffer sb = new StringBuffer();

for (ChildString s: childStrings) {

sb.append(s2.substring(s.maxStart, s.maxStart + s.maxLength));

sb.append("\n");

}

return sb.toString();

}

//求一条斜线上的公因子字符串

private void getMaxSort(int i, int j, boolean [][] array, List sortBean) {

int length = 0;

int start = j;

for (; i < a && j < b; i++,j++) {

if (array[i][j]) {

length++;

} else {

//直接add,保存所有子串,下面的判断,只保存当前最大的子串

//sortBean.add(new ChildString(length, start));

if (length == maxLength) {

sortBean.add(new ChildString(length, start));

} else if (length > maxLength) {

sortBean.clear();

maxLength = length;

sortBean.add(new ChildString(length, start));

}

length = 0;

start = j + 1;

}

if (i == a-1 || j == b-1) {

//直接add,保存所有子串,下面的判断,只保存当前最大的子串

//sortBean.add(new ChildString(length, start));

if (length == maxLength) {

sortBean.add(new ChildString(length, start));

} else if (length > maxLength) {

sortBean.clear();

maxLength = length;

sortBean.add(new ChildString(length, start));

}

}

}

}

//公因子类

class ChildString {

int maxLength;

int maxStart;

ChildString(int maxLength, int maxStart){

this.maxLength = maxLength;

this.maxStart = maxStart;

}

}

/**

* @param args

*/

public static void main(String[] args) {

// TODO Auto-generated method stub

System.out.println(new StringCompare().getMaxLengthCommonString("abcdef", "defabc"));

}

}

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

java 字符串子串_java实现字符串匹配求两个字符串的最大公共子串 的相关文章

  • Dependable Horizontal Scaling Based On Probabilistic Model Checking 阅读笔记

    一 介绍 本文提出的方法分为 基于马尔科夫决策过程 Markov Decision Processes 构建弹性动作的模型 利用模型制定具体的弹性策略 使用马尔科夫决策过程的原因 MDPs 可以捕捉问题的转移概率和不确定性 在当前状态下 不
  • leetcode两数之和c/c++

    两数之和c c 43 43 题目 xff1a 给定一个整数数组 nums 和一个目标值 target xff0c 请你在该数组中找出和为目标值的那 两个 整数 xff0c 并返回他们的数组下标 你可以假设每种输入只会对应一个答案 但是 xf
  • leetcode数据流中的第k大元素c++

    数据流中的第k大元素 设计一个找到数据流中第K大元素的类 xff08 class xff09 注意是排序后的第K大元素 xff0c 不是第K个不同的元素 你的 KthLargest 类需要一个同时接收整数 k 和整数数组nums 的构造器
  • javaweb实现登陆,注册,修改密码,显示信息,修改个人信息功能

    用户注册和登录的实现 编写JSP程序实现用户注册 登录 注销 修改密码和显示及修改用户基本信息等基本功能 通过session判断用户是否已经登录 如果未登录 请提供注册和登录功能 如果已登录 请显示用户ID 姓名 年龄等信息 并请提供注销
  • 第一次面试经历--慧扬健康

    文章目录 时间 2019 6 27日10点 面试步骤 填写基本信息 hr问问题 笔试和机试 1 填写基本信息 2 hr问问题 3 笔试和机试题目 时间 2019 6 27日10点 面试步骤 填写基本信息 hr问问题 笔试和机试 1 填写基本
  • 阿里巴巴-游戏开发面经

    文章目录 投递简历的过程 7 20号 面试 了解到的基本信息 技术面试的问题 方法一 穷举遍历 方法2 标记 方法3 快慢指针 方法4 set集合大小变化 投递简历的过程 7 17 号在上班的过程中突然实习僧的 hr 打电话给我说看到我的简
  • 支付宝支付和微信支付容易被风控可以看一下这个操作

    1 主要问题 xff1a 微信支付使用过程中容易出现微信支付商户号被交易拦截 xff0c 关闭支付权限 xff0c 关闭体现结算等风控情景 支付宝支付的过程中 xff0c 用户付款经常会提示防范兼职刷单等风控提醒 xff0c 暂停支付 xf
  • rClone 挂载Webdav

    0 习惯性的废话 好久不见甚是想念 xff0c 昨天剁手买了台Miix4低配版 xff0c 两台电脑之间的数据同步就需要考虑了 xff0c 自建了NextCloud xff0c 但把主力机一天到晚开着也不是个事 想到弄个支持Webdav的网
  • 身份证实名认证接口,实名认证API接口文档

    1 适用范围 为预防冒名注册 恶意注册等行为 xff0c 实名认证已经成为当下互联网环境下必不可少的一个环节 比如用户在进行信息发布 评论 社交等行为时 xff0c 都需要先进行实名认证 它能够帮助互联网平台对入驻用户进行真实性核验 xff
  • 商品条码API接口,免费好用

    1 前言 商品条码接口 xff0c 能实现生成指定编码信息的条形码和根据条形码code值获取商品信息 2 接口明细 注意 xff1a app id和app secret是临时秘钥 2 1 生成指定条形码 接口地址 xff1a https w
  • URL生成短链接API接口

    1 前言 URL生成短链接口 xff0c 可将长链接生成短链 xff0c 方便分发和推广 查看接口完整信息 xff1a https www idmayi com doc detail id 61 26 2 接口明细 注意 xff1a app
  • 节假日万年历API接口,免费好用

    1 前言 节假日万年历接口 xff0c 能实现查询指定日期 月份 年份 时间范围的节假日和万年历信息 xff0c 万年历的信息包含农历信息 xff0c 宜忌等信息 这个接口的主要特点是 xff0c 返回某个节日是否是工作日 xff0c 节日
  • 美女福利图片API接口,免费好用

    1 前言 美女图片福利查询接口 xff0c 能获取一些青春靓女的图片 xff0c 拿来做一些demo非常合适 查看接口完整信息 xff1a https www idmayi com doc detail id 61 15 2 接口明细 注意
  • 文本情感倾向分析API

    一 前言 文本情感倾向分析API xff0c 对带有情感色彩的主观性文本进行分析 处理 归纳和推理 二 接口文档 应用场景 商品评论的分析 电影或电视剧的评论分析 大众舆论导向分析 人物的情绪分析 人物关系分析 产品的比较分析 对某一个事件
  • 语音通知 API

    一 前言 语音通知API xff0c 通过系统发起电话直呼并播放通知内容 支持静态和动态语音 xff0c 可自定义通知内容 二 接口文档 特性 语音专线主动呼叫用户 xff0c 解决短信拦截等无法收到短信验证痛点 文本识别文本智能语音转化
  • 银行卡OCR API

    一 前言 银行卡OCR API xff0c 可以自动定位银行卡图片区域 xff0c 支持识别银行卡正面信息 xff0c 包含银行卡号 银行卡类型 银行名称等信息 二 应用场景 金融远程身份认证 使用身份证OCR和银行卡OCR实现用户信息的自
  • Centos7系统使用kubeadm方式安装k8s集群v1.26.1版本

    kubeadm方式安装k8s集群 一 准备机器 主机说明192 168 0 11master节点 xff0c 能连外网 xff0c 官网最低要求2核2G192 168 0 12node1节点 xff0c 能连外网 xff0c 官网最低要求2
  • 使用PIL和几种分类算法对标准数字图片进行识别

    详细代码见GitHub https github com nickliqian simple number recognition simple number recognition 使用PIL和几种分类算法对标准数字图片进行识别 背景 在
  • windows10修改子系统ubuntu安装路径

    1 查看当前安装的子系统版本 wsl l v 2 导出子系统文件到d盘 wsl export Ubuntu d ubuntu tar 3 注销当前子系统 wsl unregister Ubuntu 4 重新导入子系统到d盘 wsl impo
  • 字节高频题补充 检测循环依赖

    和 力扣207 课程表 相似 循环依赖检测 如 xff0c 39 A 39 39 B 39 39 B 39 39 C 39 39 C 39 39 D 39 39 B 39 39 D 39 61 gt false xff0c 39 A 39

随机推荐

  • 解决Python模块导入出现ModuleNotFoundError: No module named ‘***’的问题

    Python的模块非常多 xff0c 在安装这些模块的时候 xff0c 由于安装方法的不同 xff08 pip easyinstall xff09 xff0c 在python加载这些包时 xff0c 出现ModuleNotFoundErro
  • centos7端口管理

    1 开放端口 firewall cmd zone 61 public add port 61 5672 tcp permanent 开放5672端口 firewall cmd zone 61 public remove port 61 56
  • Rust安装后执行第一个程序遇到的问题

    当按照 https kaisery github io trpl zh cn ch01 02 hello world html 学习教程编写第一个Helloworld 执行rustc命令后汇报如下错误 G rustspace gt rust
  • 构建openvidu-loadtest工具-问题记录

    docker中创建ubuntu22 04的容器 xff0c 编译openvidu loadtest xff0c 遇到以下问题 xff0c 做备忘以便日后翻看 问题1 执行apt update更新镜像源库时发生错误 xff1a Updates
  • linux下-bash: ***: command not found解决办法

    今天在阿里云虚拟机上配置环境时出现 bash command not found错误 xff0c 网上找了一下 xff0c 方法如下 xff1a 如输入ls 出现 bash ls command not found ipconfig 出现
  • vue websocket 实现页面实时刷新

    vue websocket 实现页面实时刷新 最近公司项目需求后台web端要做实时能看到用户的登录状态以及所在位置 xff0c 说白了就是要做数据实时刷新 直接上代码吧 xff01 lt DOCTYPE html gt lt html la
  • Java 位运算详解

    目录 一 Java中支持的位运算 二 位运算规则 三 逻辑运算 xff08 一 xff09 与运算 xff08 amp xff09 一 运算规则 二 运算流程 xff08 二 xff09 或运算 xff08 xff09 一 运算规则 二 运
  • manjaro连接远程服务器

    不用下再window里面的类似XShell xff0c 只需要直接连就行 但是在ubuntu里面需要开启SSH服务 xff0c 再前边的文章里面有 xff0c 这篇只针对manjaro ssh username 64 100 100 100
  • GitLab创建SSH Key 过程

    1 首先你需要在github上或者gitlab上建立了自己的账户 xff0c 项目组已经将你加入了group 2 打开git bash xff0c 输入命令 ls al ssh xff0c 如果提示 xff0c ls cannot acce
  • wls2 ubuntu设置固定IP地址,并实现开机启动

    wls2 ubuntu设置固定IP地址 xff0c 并实现开机启动 64 echo off setlocal enabledelayedexpansion wsl shutdown Ubuntu 20 04 wsl u root d Ubu
  • 使用cmake调用swig生成库,Python调用C/C++

    前言 xff1a 项目中使用构建工具是cmake xff0c 为了集成我们的系统进去 xff0c 需要使用cmake来调用swig xff0c 然后swig生成python可执行的库 我的环境 xff1a win10swig 4 0 2py
  • C语言 : weak_alias描述

    weak alias 是一个宏 xff0c 其目的是为函数添加一个 弱 别名 xff0c 与 强 符号函数名区分 说明 如果调用函数无对应的函数无 强 符号对应的函数 xff0c 则会调用该别名对应的函数C C 43 43 函数调用是以编译
  • 结构体及结构体数组的定义

    1 结构体 结构体是用户自定义的可用的数据类型 xff0c 它允许您存储不同类型的数据项 2 结构体的定义 以学生的基本信息为例 xff0c 包括四个变量 xff1a 姓名 年龄 性别 学号 xff08 1 xff09 定义了一个结构体ST
  • Linux离线安装GitLab

    1 下载安装包 xff1a https mirrors tuna tsinghua edu cn gitlab ce yum el7 C 61 M amp O 61 D 2 rz 上传安装包到安装服务器 3 检查依赖 xff1a 分别执行以
  • 国内几个maven镜像源,国内maven仓库,阿里,华为,腾讯,网易

    span class token operator lt span mirror span class token operator gt span span class token operator lt span id span cla
  • word转pdf时图片模糊/分辨率不高解决方案

    一般我们进行文件传输时 xff0c 为了保持格式的稳定性 xff0c 经常会将doc格式转为pdf格式 xff0c 但是有时会发现转换后图片会变得异常模糊 xff0c 分辨率不高 网上有很多解决办法 xff0c 但大多比较复杂且最终效果不好
  • Vm虚拟机扩展Ubuntu系统磁盘空间

    Vm虚拟机扩展Ubuntu系统磁盘空间 前言 一般我们在安装虚拟机时都会选择默认的20G磁盘空间 xff0c 但是一旦需要搭建一两个交叉编译环境后 xff0c 20G的空间就无法满足了 xff0c 我就是出现了这样的情况 xff0c 所以也
  • linux环境下如何调鼠标灵敏度,如何在Ubuntu中配置鼠标设置

    Ubuntu是open source操作系统 xff0c 它使您可以对最小的系统模块进行大量配置 其中之一就是您要使用外部USB鼠标的方式 在本文中 xff0c 我们将介绍如何对鼠标设置进行以下更改 xff1a 将左 右按钮设置为主按钮 通
  • python获取屏幕文字_详解:四种方法教你对Python获取屏幕截图(PyQt , pyautogui)...

    前言 xff1a 今天为大家带来的内容是详解 xff1a 四种方法教你对Python获取屏幕截图 PyQt pyautogui 本文具有不错的参考意义 xff0c 希望能够帮助到大家 xff01 Python获取电脑截图有多种方式 xff0
  • java 字符串子串_java实现字符串匹配求两个字符串的最大公共子串

    本文实例讲述了java实现求两个字符串最大公共子串的方法 分享给大家供大家参考 xff0c 具体如下 xff1a 最近在项目工作中有一个关于文本对比的需求 xff0c 经过这段时间的学习 xff0c 总结了这篇博客内容 xff1a 求两个字