题目说明:

找两个字符串的最长公共子串,这个子串要求在原字符串中是连续的。比如"bab"和"caba"的最长公共子串是"ba"和"ab"。

程序代码:

#include <gtest/gtest.h>
#include <vector>
#include <algorithm>
using namespace std; int GetLCS(const string& strA, const string& strB, vector<string>& result)
{
int nLengthA = strA.length();
int nLengthB = strB.length();
int nLongest = 0;
vector<int> vecSubStrEnd; if (!nLengthA || !nLengthB)
{
return 0;
} result.clear(); // strB
// 0 1 2 3 4 5 6 7 8
// 1
// s 2
// t 3
// r 4
// A 5
// 6 char* arrRecordInfo = new char[(nLengthA + 1) * (nLengthB + 1)];
memset(arrRecordInfo, 0, (nLengthA + 1) * (nLengthB + 1)); for (int i = 1; i <= nLengthA; ++i)
{
for (int j = 1; j <= nLengthB; ++j)
{
if (strA[i-1] == strB[j-1])
{
int nNewCount = arrRecordInfo[(i-1)*(nLengthB+1) + j-1] + 1;
if (nNewCount > nLongest)
{
nLongest = nNewCount;
vecSubStrEnd.clear();
vecSubStrEnd.push_back(j);
}
else if (nNewCount == nLongest)
{
vecSubStrEnd.push_back(j);
} arrRecordInfo[i*(nLengthB+1) + j] = nNewCount;
}
}
} for (int i=0; i < vecSubStrEnd.size(); ++i)
{
int nOffset = vecSubStrEnd[i];
result.push_back(strB.substr(nOffset-nLongest, nLongest));
}
// 移除重复公共字符串
sort(result.begin(), result.end());
result.erase(unique(result.begin(), result.end()), result.end()); delete[] arrRecordInfo; return nLongest;
} // 一种节省空间的方法
// 在构造这个二维矩阵的过程中由于得出矩阵的某一行后其上一行就没用了,所以实际上在程序中可以用一维数组来代替这个矩阵
// 如果把strB的长度假设为短的那个字符串,空间更少
int GetLCS2(const string& strA, const string& strB, vector<string>& result)
{
int nLengthA = strA.length();
int nLengthB = strB.length();
int nLongest = 0;
vector<int> vecSubStrEnd; if (!nLengthA || !nLengthB)
{
return 0;
} result.clear(); // strB
// 0 1 2 3 4 5
// 1
// s 2
// t 3
// r 4
// A 5
// 6 char* arrRecordInfo = new char[nLengthB+1];
memset(arrRecordInfo, 0, nLengthB+1); for (int i = 1; i <= nLengthA; ++i)
{
for (int j = nLengthB; j >= 1; --j)
{
if (strA[i-1] == strB[j-1])
{
int nNewCount = arrRecordInfo[j-1] + 1;
if (nNewCount > nLongest)
{
nLongest = nNewCount;
vecSubStrEnd.clear();
vecSubStrEnd.push_back(j);
}
else if (nNewCount == nLongest)
{
vecSubStrEnd.push_back(j);
} arrRecordInfo[j] = nNewCount;
}
else
{
arrRecordInfo[j] = 0;
}
}
} for (int i=0; i < vecSubStrEnd.size(); ++i)
{
int nOffset = vecSubStrEnd[i];
result.push_back(strB.substr(nOffset-nLongest, nLongest));
}
// 移除重复公共字符串
sort(result.begin(), result.end());
result.erase(unique(result.begin(), result.end()), result.end()); delete[] arrRecordInfo; return nLongest;
} TEST(Algo, tLongestCommonSubString)
{
//
// "" ""
// abcdefg bdacafg
// abcabcagc abcdcagb vector<string> result;
ASSERT_EQ(GetLCS("","",result),0);
ASSERT_EQ(GetLCS("abcdefg","bdacafg",result),2);
ASSERT_EQ(GetLCS("abcabcagc","abcdcagb",result),3); ASSERT_EQ(GetLCS2("abcdefg","bdacafg",result),2);
ASSERT_EQ(GetLCS2("abcabcagc","abcdcagb",result),3);
}

[算法练习]最长公共子串(LCS)的更多相关文章

  1. 最长公共子串(LCS:Longest Common Substring)

    最长公共子串(LCS:Longest Common Substring)是一个非常经典的面试题目,本人在乐视二面中被面试官问过,惨败在该题目中. 什么是最长公共子串 最长公共子串问题的基本表述为:给定 ...

  2. 最长公共子串LCS(Longest Common Substring)

    一.问题描述 寻求两个字符串中的最大公共字串,其中子串是指字符串中连续的字符组成的,而不是像子序列,按照字符的前后顺序组成.如str1="sgabacbadfgbacst",str ...

  3. 最长公共子串(LCS) lg SP1811

    后缀自动机的一大用处就是求最长公共子串了 这道题的话题意就是给你两个字符串,求最长公共子串 做法的话是先使用一个字符串建立SAM,然后让另一个串在上面进行匹配 匹配的策略是优先匹配当前节点的下一个字符 ...

  4. 求两个字符串的最长公共子串(LCS)

    http://tianyunpu2008.blog.163.com/blog/static/6559379920089162236915/

  5. 《算法导论》读书笔记之动态规划—最长公共子序列 & 最长公共子串(LCS)

    From:http://my.oschina.net/leejun2005/blog/117167 1.先科普下最长公共子序列 & 最长公共子串的区别: 找两个字符串的最长公共子串,这个子串要 ...

  6. 华为OJ之最长公共子串

    题目描述: 对于两个给定的字符串,给出他们的最长公共子串. 题目分析: 1,最长公共子串(LCS)实际上是最长公共子序列的一种特殊情况,相当于是求连续的最长子序列.我们今天先解决这个特殊情况,后续博文 ...

  7. 算法设计 - LCS 最长公共子序列&&最长公共子串 &&LIS 最长递增子序列

    出处 http://segmentfault.com/blog/exploring/ 本章讲解:1. LCS(最长公共子序列)O(n^2)的时间复杂度,O(n^2)的空间复杂度:2. 与之类似但不同的 ...

  8. 【实习记】2014-08-29算法学习Boyer-Moore和最长公共子串(LCS)

        昨天的问题方案一:寻找hash函数,可行性极低.方案二:载入内存,维护成一个守护进程的服务.难度比较大.方案三:使用前5位来索引,由前3位增至前5位唯一性,理论上是分拆记录扩大100倍,但可以 ...

  9. 经典算法-最长公共子序列(LCS)与最长公共子串(DP)

    public static int lcs(String str1, String str2) { int len1 = str1.length(); int len2 = str2.length() ...

随机推荐

  1. hdu 5475 An easy problem(暴力 || 线段树区间单点更新)

    http://acm.hdu.edu.cn/showproblem.php?pid=5475 An easy problem Time Limit: 8000/5000 MS (Java/Others ...

  2. How Tomcat Works(七)

    本文接下来介绍并分析servlet容器,servlet容器是用来处理请求servlet资源,并为web客户端填充response对象的模块. servlet容器是org.apache.catalina ...

  3. 字符编解码的故事(ASCII,ANSI,Unicode,Utf-8)

    很久很久以前,有一群人,他们决定用8个可以开合的晶体管来组合成不同的状态,以表示世界上的万物.他们认为8个开关状态作为原子单位很好,于是他们把这称为"字节". 再后来,他们又做了一 ...

  4. winform 发布应用程序 提示 “未能注册模块(程序路径)\ieframe.dll”

    程序安装的时候出现未能注册模块(程序路径)\ieframe.dll提示 这种情况的出现,是因为引用的shdocvw.dll,目前发现了一个折中的解决方法,在安装程序里面,可以看到ieframe.dll ...

  5. (剑指Offer)面试题24:二叉搜索树的后序遍历序列

    题目: 输入一个整数数组,判断该数组是不是某个二叉搜索树的后序遍历的结果,如果是则返回true,否则返回false. 假设输入的数组的任意两个数字都互不相同. 思路: 根据二叉搜索树的后序遍历特点,很 ...

  6. jquery获取当前元素的坐标

    jquery获取当前元素的坐标 1,获取对象 var obj = $("#id号"); 或  var obj = $(this); 实例中我获取的对象是弹出窗口按钮,这样创建的新窗 ...

  7. C++的优秀特性2:inline 函数

    (转载请注明原创于潘多拉盒子) Inline函数是C++的一个很小的特性,在不计较效率的情况下,这个特性似乎可有可无.然而,C++天生是为最为广泛的应用场景设计的,因此,总会有关于效率的问题.其实,除 ...

  8. 备份服务器数据(IIS配置备份还原、任务计划、服务列表和APP)

    该脚本可以用来导出IIS配置.任务计划.服务列表和APP,同时支持Windows 2003和2008. #定义备份位置 $iisfolder = "d:\Backup_all\IIS&quo ...

  9. MS WORD 表格自己主动调整列宽,自己主动变美丽,依据内容自己主动调整

    在MS WORD中,当有大量的表格出现时,调整每一个表格的的高和宽和大小将是一件很累的事情,拖来拖去,很耗时间,并且当WORD文档达到300页以上时,调整反应很的慢,每次拖拉线后,须要等待一段时间其才 ...

  10. iOS开发——多线程OC篇&(十)多线程NSOperation基本使用

    NSOperation基本操作 一.并发数 (1)并发数:同时执⾏行的任务数.比如,同时开3个线程执行3个任务,并发数就是3 (2)最大并发数:同一时间最多只能执行的任务的个数. (3)最⼤大并发数的 ...