题目

最长公共子串

给出两个字符串,找到最长公共子串,并返回其长度。

样例

给出A=“ABCD”,B=“CBCE”,返回 2

注意

子串的字符应该连续的出现在原字符串中,这与子序列有所不同。

解题

注意:

子序列:这个序列不是在原字符串中连续的位置,而是有间隔的,如:ABCDE  和AMBMCMDMEM 最长公共子序列是ADCDE

子串:子串一定在原来字符串中连续存在的。如:ABCDEF 和SSSABCDOOOO最长公共子串是ABCD

参考链接,讲解很详细

根据子串定义,暴力破解

public class Solution {
/**
* @param A, B: Two string.
* @return: the length of the longest common substring.
*/
public int longestCommonSubstring(String A, String B) {
// write your code here
if(A == null || B == null ||A.length() ==0 || B.length() ==0)
return 0;
int lenA = A.length();
int lenB = B.length();
int longest = -1; for(int i=0 ; i <lenA ;i++){
for(int j=0; j <lenB ;j++){
int m = i;
int n = j;
int sublongest = 0;
while(m<lenA && n < lenB){
char ch1 = A.charAt(m);
char ch2 = B.charAt(n);
if(ch1 == ch2){
m++;
n++;
sublongest += 1;
}else{
break;
}
}
longest = Math.max(longest,sublongest);
}
}
return longest; }
}

Java Code

时间复杂度O(N2M2)

该解法的思路就如前所说,以字符串中的每个字符作为子串的端点,判定以此为开始的子串的相同字符最长能达到的长度。其实从表层上想,这个算法的复杂度应该只有O(n2)因为该算法把每个字符都成对相互比较一遍,但关键问题在于比较两个字符串的效率并非是O(1),这也导致了实际的时间复杂度应该是满足O(n2)和O(n3)。

上面博客中给了第一种动态规划的解法

定义数组C[lenA+1][lenB+1] C[i][j] 表示字符串A 以A[i-1] 结束 B以B[j-1] 最大相同子串的长度

当A[i-1] ==B[j-1] 的时候 C[i][j] = C[i-1][j-1] + 1 理解了子串的定义就很显然的,”连续字符串“

当A[i-1] !=B[j-1] 的时候  C[i][j] = 0

数组中的最大值就是答案了

public class Solution {
/**
* @param A, B: Two string.
* @return: the length of the longest common substring.
*/
public int longestCommonSubstring(String A, String B) {
// write your code here
// String A = "cpoe.com code";
// String B = "ccht.com code";
if(A == null || B == null ||A.length() ==0 || B.length() ==0)
return 0;
int lenA = A.length();
int lenB = B.length();
int [][] C = new int[lenA + 1][lenB + 1];
int longest = -1;
for(int i=1;i<= lenA;i++){
for(int j= 1;j<= lenB;j++){
char ch1 = A.charAt(i-1);
char ch2 = B.charAt(j-1);
if( ch1 == ch2){
C[i][j] = C[i-1][j-1] + 1;
}else{
C[i][j] = 0;
}
longest = Math.max(C[i][j],longest);
}
} return longest; }
}

Java Code

在求最长公共子序列的题目中我考虑过利用数组进行求解,但是好的解法都没有直接用到我定义的那么简单的数组

对于这个题目,字符串数组表示为:相同字符是 1

你一定会发现:子串一定在对角线上,连续对角线上1最多的那个就是最长的子串,子串的起始位置就是左上的第一个1,结束位置就是右下的最后一个一,暴力方法就是对每一个点开始的对角线1的个数,最大值就是答案,这个方法其实和上面的暴力方法一个意思的。

public class Solution {
/**
* @param A, B: Two string.
* @return: the length of the longest common substring.
*/
public int longestCommonSubstring(String A, String B) {
// write your code here
if(A == null || B == null ||A.length() ==0 || B.length() ==0)
return 0;
int lenA = A.length();
int lenB = B.length();
int [][] C = new int[lenA ][lenB ];
int longest = -1;
for(int i=0;i<lenA;i++){
for(int j= 0;j< lenB;j++){
char ch1 = A.charAt(i);
char ch2 = B.charAt(j);
if( ch1 == ch2){
C[i][j] = 1;
}else{
C[i][j] = 0;
} }
}
for(int i =0;i< lenA;i++){
for(int j=0;j<lenB;j++){
int m = i;
int n = j;
int sublongest = 0;
while(m<lenA && n <lenB){
if(C[m][n] ==1){
sublongest +=1;
m++;
n++;
}else{
break;
}
}
longest = Math.max(longest,sublongest);
}
} return longest; }
}

Java Code

上面的动态规划解法是在求出数组的同时求对角线上1的个数,上面的分开计算更容易理解,更容易想到动态规划的解法。

上面博客还要其他方法,待更新。。。

lintcode :最长公共子串的更多相关文章

  1. lintcode 77.Longest Common Subsequence(最长公共子序列)、79. Longest Common Substring(最长公共子串)

    Longest Common Subsequence最长公共子序列: 每个dp位置表示的是第i.j个字母的最长公共子序列 class Solution { public: int findLength ...

  2. lintcode-79-最长公共子串

    79-最长公共子串 给出两个字符串,找到最长公共子串,并返回其长度. 注意事项 子串的字符应该连续的出现在原字符串中,这与子序列有所不同. 样例 给出A="ABCD",B=&quo ...

  3. [Data Structure] LCSs——最长公共子序列和最长公共子串

    1. 什么是 LCSs? 什么是 LCSs? 好多博友看到这几个字母可能比较困惑,因为这是我自己对两个常见问题的统称,它们分别为最长公共子序列问题(Longest-Common-Subsequence ...

  4. HDU 1503 带回朔路径的最长公共子串

    http://acm.hdu.edu.cn/showproblem.php?pid=1503 这道题又WA了好几次 在裸最长公共子串基础上加了回溯功能,就是给三种状态各做一个 不同的标记.dp[n][ ...

  5. 最长公共子序列PK最长公共子串

    1.先科普下最长公共子序列 & 最长公共子串的区别: 找两个字符串的最长公共子串,这个子串要求在原字符串中是连续的.而最长公共子序列则并不要求连续. (1)递归方法求最长公共子序列的长度 1) ...

  6. 动态规划(一)——最长公共子序列和最长公共子串

    注: 最长公共子序列采用动态规划解决,由于子问题重叠,故采用数组缓存结果,保存最佳取值方向.输出结果时,则自顶向下建立二叉树,自底向上输出,则这过程中没有分叉路,结果唯一. 最长公共子串采用参考串方式 ...

  7. 字符串hash + 二分答案 - 求最长公共子串 --- poj 2774

    Long Long Message Problem's Link:http://poj.org/problem?id=2774 Mean: 求两个字符串的最长公共子串的长度. analyse: 前面在 ...

  8. 后缀数组(模板题) - 求最长公共子串 - poj 2774 Long Long Message

    Language: Default Long Long Message Time Limit: 4000MS   Memory Limit: 131072K Total Submissions: 21 ...

  9. 最长公共子串 NYOJ 36

    http://acm.nyist.net/JudgeOnline/problem.php?pid=36 最长公共子序列 时间限制:3000 ms  |  内存限制:65535 KB 难度:3   描述 ...

随机推荐

  1. maven学习手记 - 2

    学习目标 maven 的插件和目标: maven 的生命周期和阶段.   前言 在手记1中看到执行 mvn clean package 时,maven 自动执行了compile 和 test 操作. ...

  2. 扒一扒编辑距离(Levenshtein Distance)算法

    最近由于工作需要,接触了编辑距离(Levenshtein Distance)算法.赶脚很有意思.最初百度了一些文章,但讲的都不是很好,读起来感觉似懂非懂.最后还是用google找到了一些资料才慢慢理解 ...

  3. Jquery 1.8.2 click function - 动态

    Jquery 动态按钮方法如下:   $("#parentID").on("click",'.classname',function(){$(this).par ...

  4. cnblogs用户体验

    在使用博客园的这段时间内,我们感觉有优点也有缺点,下面谈谈我们的看法: 1.是什么样的用户?有什么样的心理?对cnblogs的期望值是什么? 我们是学生用户,使用cnblogs主要是提交作业记录自己的 ...

  5. liferay MVCActionCommand的用法及例子

    在liferay7中把portlet中的控制层拆成了3个部分: 1.MVCActionCommand 2.MVCRenderCommand 3.MVCRecourceCommand 至于为什么要拆出来 ...

  6. 在listener或者工具中使用spring容器中的bean实例

    在项目中经常遇见需要在Listener中或者工具中使用Spring容器中的bean实例,由于bean不能在stataic的类中使用. 介绍一种方式: public class SpringTool { ...

  7. netty 粘包问题处理

    netty 粘包问题处理 key words: netty 粘包 解包 半包 TCP 一般TCP粘包/拆包解决办法 定长消息,例如每个报文长度固定,不够补空格 使用回车换行符分割,在包尾加上分割符,例 ...

  8. bzoj 1565 最大权闭合子图

    因为每个植物都有保护的点(每排相邻的右面的算是保护左面的),所以连他和保护 的点一条边,然后每个点有自己的权值,要找到最大的权值且满足每个点在访问时他 的前驱一定被访问,那么反向建边,转化为后继必须访 ...

  9. linux install

    http://www.ubuntu.org.cn/index_kylin 先在官网下个Ubuntu  是个iso 然后下个UltraISO 是个软件 插好空u盘 打开软件 在菜单栏上 点击 文件-&g ...

  10. 项目分析(PLUG)

    plug过程 .INIT_PLUG #define INIT_PLUG Plug::InitPlug g_InitPlug(true); //共享内存数据结构 struct PlugShareMemo ...