[日常训练]string
Description
给定一个长度为$n$的字符串,串中的字符保证是前$k$个小写字母。你可以在字符串后再添加$m$个字符,使得新字符串所包含的不同的子序列数量尽量多。当然,前提是只能添加前$k$个小写字母。求新的长度为$n+m$的串最多的不同子序列数量。答案对$10^9+7$取模。
Input
输入第一行两个数$m,k$。
接下来一行一个字符串,长度为$n$,表示原始的字符串$s$。
Output
一个数,表示答案。
Sample Input
1 3
ac
Sample Output
8
HINT
$n,m\;\leq\;10^6,k\;\leq\;26$
Solution
当$m=0$时,
$lst[i]$表示字符$i$上一次出现的位置,
$f[i]$表示以第$i$位结尾的新出现的不同的子序列的个数.
以第$x(lst[i]\;\leq\;x<i)$位结尾的新出现的子序列末尾加上$s[i]$为一个新的子序列.(反证法可证$x(0<x<lst[i])$不可行)
$f[i]=\sum_{j=lst[s[i]]}^{i-1}f[j]$.
这个可以用前缀和优化.
当$m\not=0$时,
设$sum[i]=\sum_{j=1}^{i}f[j]$,
则$f[i]=sum[i-1]-sum[lst[j]-1](n<i\;\leq\;n+m)$
$f[i]$最大,即$lst[j]-1$最小.
#include<cmath>
#include<ctime>
#include<queue>
#include<stack>
#include<cstdio>
#include<vector>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#define K 2000005
#define M 1000000007
using namespace std;
int s[K],sum,tmp,m,n,t;
bool u[K];char c;
int f[K],lst[K];
inline void Aireen(){
scanf("%d%d",&m,&t);
c=getchar();
for(n=1;scanf("%c",&c)==1;++n){
if(!(c>='a'&&c<='z'))
break;
if(lst[c-'a'])
f[n]=(s[n-1]-s[lst[c-'a']-1]+M)%M;
else f[n]=(s[n-1]+1)%M;
s[n]=(s[n-1]+f[n])%M;
lst[c-'a']=n;
}
--n;
if(t) for(int i=n+1,j,k;i<=n+m;++i){
k=lst[0];j=0;
for(int l=1;l<t;++l){
if(lst[l]<k){
k=lst[l];j=l;
}
}
printf("j=%d\n",j);
if(lst[j])
f[i]=(s[i-1]-s[lst[j]-1]+M)%M;
else f[i]=(s[i-1]+1)%M;
s[i]=(s[i-1]+f[i])%M;
lst[j]=i;
}
printf("%d\n",(s[n+m]+1)%M);
}
int main(){
freopen("string.in","r",stdin);
freopen("string.out","w",stdout);
Aireen();
fclose(stdin);
fclose(stdout);
return 0;
}
因为卡空间$1MB$,每次转移只与$f[lst[i]-1]$有关,所以只需$O(k)$的空间.
#include<cmath>
#include<ctime>
#include<queue>
#include<stack>
#include<cstdio>
#include<vector>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#define K 26
#define M 1000000007
using namespace std;
int s[K],lst[K],sum,tmp,m,n,t;
char c;
inline void Aireen(){
scanf("%d%d",&m,&t);
c=getchar();
for(n=1;scanf("%c",&c)==1;++n){
if(!(c>='a'&&c<='z'))
break;
tmp=s[c-'a'];s[c-'a']=sum;
if(lst[c-'a']) sum=((sum<<1)%M-tmp+M)%M;
else sum=((sum<<1)+1)%M;
lst[c-'a']=n;
}
--n;
if(t) for(int i=1,j,k;i<=m;++i){
k=lst[0];j=0;
for(int l=1;l<t;++l){
if(lst[l]<k){
k=lst[l];j=l;
}
}
tmp=s[j];s[j]=sum;
if(lst[j]) sum=((sum<<1)%M-tmp+M)%M;
else sum=((sum<<1)+1)%M;
lst[j]=i+m;
}
printf("%d\n",(sum+1)%M);
}
int main(){
freopen("string.in","r",stdin);
freopen("string.out","w",stdout);
Aireen();
fclose(stdin);
fclose(stdout);
return 0;
}
[日常训练]string的更多相关文章
- 「日常训练」ZgukistringZ(Codeforces Round #307 Div. 2 B)
题意与分析(CodeForces 551B) 这他妈哪里是日常训练,这是日常弟中弟. 题意是这样的,给出一个字符串A,再给出两个字符串B,C,求A中任意量字符交换后(不限制次数)能够得到的使B,C作为 ...
- 「日常训练」 Fire!(UVA-11624)
与其说是训练不如说是重温.重新写了Java版本的代码. import java.util.*; import java.math.*; import java.io.BufferedInputStre ...
- 「日常训练」Common Subexpression Elimination(UVa-12219)
今天做的题目就是抱佛脚2333 懂的都懂. 这条题目干了好几天,最后还是参考别人的代码敲出来了,但是自己独立思考了两天多,还是有收获的. 思路分析 做这条题我是先按照之前的那条题目(The SetSt ...
- 集训队日常训练20181117 DIV2
大佬们一顿操作猛如虎,拼命AC强啊 4262: 区间异或 Time Limit(Common/Java):1000MS/3000MS Memory Limit:65536KByteTotal ...
- [日常训练]article
Description 小今天来写作文啦! 小非常善于堆砌辞藻.在洋洋洒洒写了一长篇之后,小发现作文中很多段落都似曾相识.小认为,如果一段字符在文章开头,结尾和中间都出现过,那么这段字符就可以被认为是 ...
- 日常训练 dfs 之 拓扑排序
今天被拓扑排序给折磨了一天,主要就是我的一个代码有点小bug,真难找... 先来看看我今天写的题目吧! C. Fox And Names Fox Ciel is going to publish a ...
- 日常训练赛 Problem C – Complete Naebbirac’s sequence
比赛链接https://vjudge.net/contest/256988#status/17111202012/C/0/ 大意:三个操作,使得输入的数中,从1-n,每一个数出现的次数相同. wa代码 ...
- 【日常训练】 Help Greg the Dwarf(CodeForces-99E)
题意与分析 题意是这样的,问你把一个长方形从一个L型街道的一端移动到另一端,固定了该长方形的长,求他的最大宽. 这种问题我是第一次独立解决(以前都是抱队友大腿QAQ),现在没法子只好自己硬着头皮做,看 ...
- 【日常训练】Help Victoria the Wise(Codeforces 99C)
题意与分析 这题意思是这样的:在正方体的六面镶嵌给定颜色的宝石(相同颜色不区分),然后问最多有几种彼此不等价(即各种旋转过后看起来一致)的方案. 其实可以乱搞,因为范围只有720.求出全排列,然后每个 ...
随机推荐
- 【夯实PHP基础】PHP的反射机制
本文地址 分享提纲: 1. 介绍 2. 具体例子 2.1 创建Persion类 2.2 反射过程 2.3 反射后使用 1. 介绍 -- PHP5添加了一项新的功能:Reflection.这个功能使得p ...
- Java中日期的转化
4.如何取得年月日.小时分秒? 创建java.util.Calendar实例(Calendar.getInstance()),调用其get()方法传入不同的参数即可获得参数所对应的值,如:calend ...
- JAVA的序列化和持久化的区别与联系
持久化(Persistence) 即把数据(如内存中的对象)保存到可永久保存的存储设备中(如磁盘).持久化的主要应用是将内存中的对象存储在关系型的数据库中,当然也可以存储在磁盘文件中.XML数据文 ...
- 利用Java动态生成 PDF 文档
利用Java动态生成 PDF 文档,则需要开源的API.首先我们先想象需求,在企业应用中,客户会提出一些复杂的需求,比如会针对具体的业务,构建比较典型的具备文档性质的内容,一般会导出PDF进行存档.那 ...
- swift 如何在IOS应用图标上添加消息数
在应用图标右上角添加消息数提醒,可以很方便的告知用户该应用中有无新消息需要处理.下面用xcode 7.3.1来简要说明一下如何用swift语言进行此功能的实现. 1.修改 AppDelegate.sw ...
- 初识html5的localStorage本地存储
一.概述 HTML5 提供了两种在客户端存储数据的新方法: localStorage - 没有时间限制的数据存储 sessionStorage - 针对一个 session 的数据存储 之前,这些都是 ...
- 怎样给div增加resize事件
当浏览器窗口被调整到一个新的高度或宽度时,就会触发resize事件,这个事件在window上面触发,那么如何给div元素增加resize事件,监听div的高度或宽度的改变呢? 先来回答另一个问题,监听 ...
- Android 防止多次点击事件
恐怕大家都会遇到这样的问题,一个点击事件多次触发,导致,同样的内容提交了多次,或者说弹出多个页面... 下面是简单的方案,大家可以试一试 原理很简单,当我们第一次点击的时候,把按钮变成不可点击状态. ...
- ASP.NET MVC 5 01 - ASP.NET概述
本篇目录: ASP.NET 概述 .NET Framework 与 ASP.NET ASP.NET MVC简介 ASP.NET的特色和优势 典型案例 ▁▃▅ ASP.NET概述 ▅▃▁ 目前开发B/S ...
- ZooKeeper:数据模型
ZooKeeper数据模型 ZNode ZNode 分类 Stat Watcher Watcher工作原理 Watcher事件说明 Watcher注册 事件发布 示例 ZooKeeper 数据模型 整 ...