您的位置:首页 > 其它

华为OJ——查找两个字符串a,b中的最长公共子串

2017-07-31 15:55 537 查看
题目描述

查找两个字符串a,b中的最长公共子串。若有多个,输出在较短串中最先出现的那个。

输入描述:

输入两个字符串

输出描述:

返回重复出现的字符

示例1

输入

  abcdefghijklmnop

  abcsafjklmnopqrstuvw

输出

   jklmnop

实现代码:

方法一:

思路:

  ①动态规划,注意c的长度需要预留n+1,方便递归初始化

  ②若出现多个,需要输出最短的字符串中,最先出现的一个子字符串,所以在做递归之前,需要 先判断谁短谁长。

  

package cn.c_shuang.demo62;

import java.util.Scanner;
/**
* 查找两个字符串a,b中的最长公共子串
* @author Cshuang
*
*/
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
while (in.hasNextLine()){
String s1=in.nextLine();
String s2=in.nextLine();
System.out.println(lonComSub(s1,s2));
}
in.close();
}

private static String lonComSub(String a, String b) {
int aLen=a.length()+1;
int bLen=b.length()+1;//子所以要限制长度+1,方便c[0][0]
int end=0;
int max=0;
if(aLen>bLen){//将较短的字符串放在前面
int temp;
temp=aLen;
aLen=bLen;
bLen=temp;

String s;
s=a;
a=b;
b=s;
}
//事实上真正计数的从c[1][1]开始
int[][] c=new int[aLen][bLen];

for (int i = 1; i < aLen; i++) {
for (int j = 1; j < bLen; j++) {
if(a.charAt(i-1)==b.charAt(j-1)){
c[i][j] = c[i-1][j-1]+1;
}else{
c[i][j]=0;
}
if(c[i][j]>max){
end=i;
max=c[i][j];
}
}
}
return a.substring(end-max,end);
}
}


方法二:

思路:

  直接判断字符串是否包含另一个字符串的子字符串,来得出最长公共子串

import java.util.*;
public class Main{
public static void main(String[] args){
Scanner in = new Scanner(System.in);
while(in.hasNext()){
String s1 = in.nextLine();
String s2 = in.nextLine();
String max = s1.length() >= s2.length()?s1:s2;
String min = s1.length() >= s2.length()?s2:s1;
int l = 0;
String s ="";
for(int i=0;i<min.length();i++){
for(int j=i+1;j<=min.length();j++){
if(max.contains(min.substring(i,j)) && j-i>l){
l=j-i;
s=min.substring(i,j);
}
}
}
System.out.println(s);
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  动态规划 递归 华为