题目描述 Description

有两个仅包含小写英文字母的字符串A和B。现在要从字符串A中取出k个互不重叠的非空子串,然后把这k个子串按照其在字符串A中出现的顺序依次连接起来得到一个新的字符串,请问有多少种方案可以使得这个新串与字符串B相等?注意:子串取出的位置不同也认为是不同的方案。

输入描述 Input Description

第一行是三个正整数n,m,k,分别表示字符串A的长度,字符串B的长度,以及问题描述中所提到的k,每两个整数之间用一个空格隔开。

第二行包含一个长度为n的字符串,表示字符串A。 第三行包含一个长度为m的字符串,表示字符串B。

输出描述 Output Description

 

输出共一行,包含一个整数,表示所求方案数。由于答案可能很大,所以这里要求输出答案对1,000,000,007取模的结果。

样例输入 Sample Input

【Input1】

6 3 1

aabaab

aab

【Input2】

6 3 2

aabaab

aab

【Input3】

6 3 3

aabaab

aab

样例输出 Sample Output

【Output1】

2

【Output2】

7

【Output3】

7

数据范围及提示 Data Size & Hint

对于第1组数据:1≤n≤500,1≤m≤50,k=1;

对于第2组至第3组数据:1≤n≤500,1≤m≤50,k=2;

对于第4组至第5组数据:1≤n≤500,1≤m≤50,k=m;

对于第1组至第7组数据:1≤n≤500,1≤m≤50,1≤k≤m;

对于第1组至第9组数据:1≤n≤1000,1≤m≤100,1≤k≤m;

对于所有10组数据:1≤n≤1000,1≤m≤200,1≤k≤m。

——————————————————————————题解

迟到一年的整理,然而看着看着有思路了还是不会写,orz

那么记一下思路吧,这道题是要压缩的,它会卡空间的,要滚动数组。

我们按照三维的来考虑,我们再记一个数组f[i][j][k]为选择第i位后的a串前i个b串前j个选择k个子串有几种组合方式

s[i][j][k]是a串前i个b串前j个选择k个子串有几种组合方式,f,s数组的差别是一个选了第i个,一个不一定选了第i个

然后和最长公共子串一样

f数组的递推思路:要是a的第i位能够和b的第j位匹配上,我们选择第i位当一个串是一种情况,这个时候我们把s数组的s[i-1][j-1][k-1]转移过来就可以了,那么i-1显然也要和j-1匹配上才能多加上额外的一些情况,如果i-1和j-1都匹配不上就不能再往左延伸了,所以如果a[i]!=b[j]相当于一个公共子串被切断一样,f[i][j][k]=0

所以:

f[i][j][k]=f[i-1][j-1][k]+s[i-1][j-1][k-1] (a[i]==b[j])

f[i][j][k]=0 (a[i]!=b[j])

s数组的递推思路:当a[i]==b[j]时,我们可以选i也可以不选,我们加上f数组就好了和不选的情况s[i-1][j][k]就可以了,如果不相同那就肯定不选了,此时f数组为0,我们无需特判

s[i][j][k]=f[i][j][k]+s[i-1][j][k]

压缩的思路:由于我们的每次i都只与i-1有关,所以我们可以把第一维压缩掉,因为后面的j要用到j-1的情况,所以我们从后往前更新,k同理,也是从后往前,然后要控制范围是min(K,j)

 #include <queue>
#include <cstdio>
#include <vector>
#include <cstring>
#include <algorithm>
#define mo 1000000007
#define siji(i,x,y) for(int i=(x);i<=(y);i++)
#define gongzi(j,x,y) for(int j=(x);j>=(y);j--)
#define xiaosiji(i,x,y) for(int i=(x);i<(y);i++)
#define sigongzi(j,x,y) for(int j=(x);j>(y);j--)
#define pii pair<int,int>
#define fi first
#define se second
#define mo 1000000007
using namespace std;
typedef long long ll;
int n,m,k;
int f[][],s[][];
char a[],b[];
int main(int argc, char const *argv[])
{
//freopen("f1.in","r",stdin);
scanf("%d%d%d",&n,&m,&k);
scanf("%s%s",a+,b+);
s[][]=;//如果有第一个相同我们就转移了
siji(i,,n) {
gongzi(j,m,) {
if(a[i]==b[j]) {
gongzi(h,min(k,j),) {//相等的话开始递推,数组里原先存着的是i-1,我们更新成i
f[j][h]=(f[j-][h]+s[j-][h-])%mo;
s[j][h]=(s[j][h]+f[j][h])%mo;
}
}
else fill(f[j],f[j]+min(k,j)+,);//不相等就是0
}
}
printf("%d\n",s[m][k]);
}

noip2015Day2T2-子串的更多相关文章

  1. Vijos1982 NOIP2015Day2T2 子串 substring 动态规划

    子串 (substring.cpp/c/pas) 题目链接 [问题描述]有两个仅包含小写英文字母的字符串 A 和 B.现在要从字符串 A 中取出 k 个 互不重叠 的非空子串,然后把这 k 个子串按照 ...

  2. NOIP2015Day2T2子串(字符串dp)

    又被“if(a=b)”坑了QAQ...写C++还是得开Warning,这么久了pascal还没改过来咋回事啊QWQ 题目大意就不说了OWO 网上的题解都不怎么看得懂啊...好像写得都很乱?还是我太sb ...

  3. LeetCode[5] 最长的回文子串

    题目描述 Given a string S, find the longest palindromic substring in S. You may assume that the maximum ...

  4. 最长回文子串-LeetCode 5 Longest Palindromic Substring

    题目描述 Given a string S, find the longest palindromic substring in S. You may assume that the maximum ...

  5. C语言计算字符串子串出现的次数

    #include<stdio.h>#include<string.h>int substring(char *str,char *str1);//函数原型int main(vo ...

  6. [LeetCode] Longest Substring with At Most Two Distinct Characters 最多有两个不同字符的最长子串

    Given a string S, find the length of the longest substring T that contains at most two distinct char ...

  7. [LeetCode] Minimum Window Substring 最小窗口子串

    Given a string S and a string T, find the minimum window in S which will contain all the characters ...

  8. [LeetCode] Substring with Concatenation of All Words 串联所有单词的子串

    You are given a string, s, and a list of words, words, that are all of the same length. Find all sta ...

  9. [LeetCode] Longest Substring Without Repeating Characters 最长无重复子串

    Given a string, find the length of the longest substring without repeating characters. For example, ...

  10. mysql判断一个字符串是否包含某子串

    使用locate(substr,str)函数,如果包含,返回>0的数,否则返回0 例子:判断site表中的url是否包含'http://'子串,如果不包含则拼接在url字符串开头 update ...

随机推荐

  1. java 企业网站源码模版 有前后台 springmvc SSM 生成静态化

    java 企业网站源码 前后台都有 静态模版引擎, 代码生成器大大提高开发效率 系统介绍 点击:获取地址 : 1.网站后台采用主流的 SSM 框架 jsp JSTL,网站后台采用freemaker静态 ...

  2. jQuery+HTML5声音提示

    WEB应用中,有时需要播放特定的声音,比如有新消息或者在线聊天消息声音提示,以前我们通过flash实现,今天我们将使用jQuery和HTML5结合示例来实现如何把声音提示带入WEB应用中. 在本例中, ...

  3. 浅谈JAVA中字符串常量的储存位置

    在讲述这些之前我们需要一些预备知识: java中的内存被分成以下部分: 1.栈区:由编译器自动分配释放,具体方法执行结束后,系统自动释放JVM内存资源. 其作用有保存局部变量的值,包括:1.用来保存基 ...

  4. [前端性能提升]--图片转化为base64

    图片的 base64 编码就是可以将一副图片数据编码成一串字符串,使用该字符串代替图像地址 意义:网页上的每一个图片,都是需要消耗一个 http 请求下载而来的(所有才有了 csssprites 技术 ...

  5. 基于python第三方requests 模块的HTTP请求类

    使用requests模块构造的下载器,首先安装第三方库requests pip install requests 1 class StrongDownload(object): def __init_ ...

  6. js 技巧1

    1. 使用===取代==    ==和!=操作符会在需要的情况下自动转换数据类型.但===和!==不会,它们会同时比较值和数据类型,这也使得它们要比==和!=快. "){ //速度慢 } & ...

  7. Python操作redis、memcache和ORM框架_Day13

    一.memcache Memcached 是一个高性能的分布式内存对象缓存系统,用于动态Web应用以减轻数据库负载.它通过在内存中缓存数据和对象来减少读取数据库的次数,从而提高动态.数据库驱动网站的速 ...

  8. fileupload实现控制大小进行图片上传

    if ($(".img-upload").length > 0) { $('.img-upload').fileupload({ type: 'POST', url: &qu ...

  9. linux服务器没网情况下手动安装软件几个方法

    1,找到一个有网的服务器,使用yumdownloader gcc,获取需要的rmp包: 2,在http://pkgs.org 下下载所需要的rpm包

  10. 【hihoCoder 1466】后缀自动机六·重复旋律9

    http://hihocoder.com/problemset/problem/1466 建出A串和B串的两个后缀自动机 对后缀自动机的每个状态求出sg值. 求出B串的\(sum(x)\),表示B有多 ...