Description

字符序列的子序列是指从给定字符序列中随意地(不一定连续)去掉若干个字符(可能一个也不去掉)后所形成的字符序列。令给定的字符序列X=“x0,x1,…,xm-1”,序列Y=“y0,y1,…,yk-1”是X的子序列,存在X的一个严格递增下标序列<i0,i1,…,ik-1>,使得对所有的j=0,1,…,k-1,有xij = yj。例如,X=“ABCBDAB”,Y=“BCDB”是X的一个子序列。对给定的两个字符序列,求出他们最长的公共子序列长度,以及最长公共子序列个数。

Input

第1行为第1个字符序列,都是大写字母组成,以”.”结束。长度小于5000。
第2行为第2个字符序列,都是大写字母组成,以”.”结束,长度小于5000。

Output

第1行输出上述两个最长公共子序列的长度。
第2行输出所有可能出现的最长公共子序列个数,答案可能很大,只要将答案对100,000,000求余即可。
 

Sample Input

ABCBDAB.
BACBBD.

Sample Output

4
7
 
反思:题目虽然看题解看懂了,自己也敲出来了,但是当别人问的时候不能清晰的讲出自己思路(甚至还讲错了,这个是真TM尴尬),这样是失败的,虽然AC了,然并卵;
   这题第2问严格的来说并不能算动态规划(不满足无后效性),只是借用其中状态如何转移;
 
题解:第一问模板题,第二问不会写
  有2个问题:第LCS的个数,代码会爆空间(需要滚动数组)
  f[i][j]表示A前i位,B前j位的最长公共子序列长度,用g[i][j]表示A前i位,B前j位的最长公共子序列数目

  g[i][j]如何转移呢?考虑这是从那一步推过来的,
  比如当 f[i][j]=f[i−1][j],就可以认为从f[i-1][j]转移过来,
  那么g[i][j]=g[i-1][j];
  那么有如下关系式:
  当f[i][j]=f[i−1][j],g[i][j]+=g[i−1][j]

  当f[i][j]=f[i][j−1],g[i][j]+=g[i][j−1]

  当a[i]=b[j]且f[i][j]=f[i−1][j−1]+1,g[i][j]+=g[i−1][j−1],看起来好像没啥问题,but...样例都没法过,Orz

  其实是忽略了一种情况(本质上是对这个状态转移不是特别清晰),

  当a[i]≠b[j],并且f[i][j]=f[i−1][j−1]f[i][j]=f[i−1][j−1],(就是a,b的最后一位均没有匹配,会导致上面的2个if条件都会满足,

  g[i][j]同时累计上g[i-1][j]和g[i][j-1]时,明显有重复的情况 。

  

 #include <iostream>
#include <cstdio>
#include <cstring>
using namespace std; const int mod=;
const int maxn=;
char a[maxn], b[maxn];
int f[][maxn],g[][maxn]; int main()
{
//freopen("in.txt", "r", stdin); scanf("%s",a+);scanf("%s",b+);
int n=strlen(a+)-, m=strlen(b+)-; g[][]=;
for(int j=;j<=m;j++)
g[][j]=; for(int i=;i<=n;i++)
{
int now=i&,pre=now^;
for(int j=; j<=m; j++)
{
f[now][j]=max(f[pre][j], f[now][j-]);
if(a[i]==b[j])
{
f[now][j]=max(f[now][j],f[pre][j-]+);
if(f[now][j]==f[pre][j-]+)
g[now][j]=g[pre][j-];
}
else
{
g[now][j]=;
if(f[now][j]==f[pre][j-])
g[now][j]-=g[pre][j-];
}
if(f[now][j]==f[pre][j])
g[now][j]=(g[now][j]+g[pre][j])%mod; if(f[now][j]==f[now][j-])
g[now][j]=(g[now][j]+g[now][j-])%mod;
}
}
printf("%d\n%d",f[n&][m],g[n&][m]);
return ;
}

BZOJ 2423 (求LCS的长度和种类数)的更多相关文章

  1. 【转】最长公共子序列(LCS),求LCS长度和打印输出LCS

    求LCS的长度,Java版本: public static int LCS(int[]a,int[] b) { int [][]c=new int[a.length+1][b.length+1]; f ...

  2. 字符串暴力枚举子序列求LCS

    题意: 求n个串里的LCS,长度相同时按照字典序排序 solution: 断环为链,二进制枚举子序列,压入vector,按照字典序排序 把出现次数为n的,压入第二个vector 输出最长的第二个vec ...

  3. UVA 10635 Prince and Princess—— 求LCS(最长公共子序列)转换成 求LIS(最长递增子序列)

    题目大意:有n*n个方格,王子有一条走法,依次经过m个格子,公主有一种走法,依次经过n个格子(不会重复走),问他们删去一些步数后,重叠步数的最大值. 显然是一个LCS,我一看到就高高兴兴的打了个板子上 ...

  4. poj 1961 Period【求前缀的长度,以及其中最小循环节的循环次数】

    Period Time Limit: 3000MS   Memory Limit: 30000K Total Submissions: 14653   Accepted: 6965 Descripti ...

  5. 【c语言】实现一个函数,求字符串的长度,不同意创建第三方变量

    // 实现一个函数,求字符串的长度.不同意创建第三方变量. #include <stdio.h> #include <assert.h> int my_strlen_no(ch ...

  6. char a[] = "ab\0123\098"; 求a的长度

      原因: \0表示后面的字符是八进制(\ddd); 8进制=10进制( 10是'\n' 的ASCII码): 当\0后面有数字,且数字范围在0~7之间时,为8进制转义.如'\012': 当\0后面没有 ...

  7. C语言中求字符串的长度

    在C语言中求字符串的长度,可以使用sizeof()函数和strlen()函数,后者需要引入string.h (#include <string.h>) 因为C语言字符串是以 \0 结尾表示 ...

  8. 谈谈"求线段交点"的几种算法(js实现,完整版)

    "求线段交点"是一种非常基础的几何计算, 在很多游戏中都会被使用到. 下面我就现学现卖的把最近才学会的一些"求线段交点"的算法总结一下, 希望对大家有所帮助.  ...

  9. c# 用户输入一个字符串,求字符串的长度

    C#  用户输入一个字符串,求字符串的长度使用字符串的length: class Program { static void Main(string[] args) { Console.WriteLi ...

随机推荐

  1. git fork代码并修改胡提交到自己的git仓库

    最近在参加阿里天池大数据中间件比赛(毫无头绪,打酱油中).看参赛要求,需要将官网的git工程clone下来,在此基础上做修改后提交到自己的仓库中. 由于以前并没有使用过git,所以差了比较多的资料,做 ...

  2. RunExecuteFile

    using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using S ...

  3. xcode工程编译错误之iOS解决CUICatalog: Invalid asset name supplied问题

    [问题分析]: 这个问题其实是老问题,产生原因就是因为在使用的时候 [UIImage imageNamed:]时,图片不存在或者传入的图片名为nil. [解决方法]: 添加一个系统断点,来判断如果图片 ...

  4. 20165317Java实验五 网络编程与安全

    实验五 网络编程与安全 一.中缀转后缀 参考http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA 结对实现中缀表达式转后缀表达式的功能 MyBC.ja ...

  5. CF280D k-Maximum Subsequence Sum

    题目链接:洛谷 题目大意:[题意翻译已经够直白了] 首先,相信大家一开始都是想去直接dp,但是发现复杂度不对. 于是我们考虑一个黑科技:模拟费用流(相信大部分人看见数据范围就绝对不会想到费用流) 我们 ...

  6. [面试题]vi/vim快捷键及面试题系列

    选择 vi保存退出命令 w! wq! q! www vi移动光标到文件最后一行 G g ggg 4444 vi删除一行的命令 dd d D shift+4 在vi编辑器中的命令模式下,键入()可在光标 ...

  7. 012-mac下shell,zsh,oh-my-zsh,以及插件

    1.查看当前shell echo $SHELL 2.查看安装的shell cat /etc/shells 查看可知 /bin/bash /bin/csh /bin/ksh /bin/sh /bin/t ...

  8. python基础之 列表,元组,字典

    other help(str.strip) #查看是否有返回值以及返回值类型[] :称为索引操作符 1.列表 列表相比字符串来说能存储大量数据的python的基本数据类型,并且也拥有字符串的一些方法( ...

  9. CSS-对于IE的兼容问题处理

    css兼容问题 兼容问题 1.文字本身的大小不兼容.同样是font-size:14px的宋体文字,在不同浏览器下占的空间是不一样的,ie下实际占高16px,下留白3px,ff下实际占高17px,上留白 ...

  10. 【JVM】-NO.112.JVM.2 -【JDK11 HashMap详解-2-tab[i = (n - 1) & hash])剖析】

    Style:Mac Series:Java Since:2018-09-10 End:2018-09-10 Total Hours:1 Degree Of Diffculty:5 Degree Of ...