P8001 Easy Strings Merging
题意
给定 个 01 串,每次你可以从某个串开头移除一个字符并把它加入一个新串 的末尾。最大化 中相邻两个字符相同的对数。
分析
一段长为 的同样字符中相邻两个字符相同的对数显然为 ,但如果拆成 段只有 对,所以我们只要使同种字符尽量合起来,总段数尽可能少即可,显然题目给的是 个栈,我们一次性把所有栈顶的 取完,再取完所有的 ,再 以此类推,直到全都取完,这样得到的段数肯定最少,相当于把每个栈按字符种类划分成几段,将每段对数依次放在数组中,把每个栈的贡献叠合,就可以计算答案了。
然而这样写完你发现过不了,原来第一次有从 或 开始取两种情况,聪明的你一定能想到,合理运用三大键 Ctrl
、C
、V
就可以通过。
代码
#include<bits/stdc++.h>
#define ll long long
using namespace std;
long long read(){
long long x=0,f=1;char ch=getchar();
while(!isdigit(ch)){if(ch=='-') f=-1;ch=getchar();}
while(isdigit(ch)){x=x*10+ch-48;ch=getchar();}
return x*f;
}
void write(long long x){
if(x<0) putchar('-'),x=-x;
if(x>9) write(x/10);
putchar(x%10+'0');
}
const int N=1e6+10;
int n,lst;
ll ans1,d1[N],d2[N],ans2,mx;
int c[N];
int main(){
n=read();
for(int i=1,j,D;i<=n;i++){
j=1;
while((c[j]=getchar())!='\n')
c[j++]-='0';
lst=1;
if(c[1]^1)
D=1;
else
D=2;
for(int k=2;k<=j;k++)
if(c[k]^c[k-1]){
d1[D++]+=k-lst;
lst=k;
}
mx=max(mx,(ll)D-1);
lst=1;
if(c[1]^0)
D=1;
else
D=2;
for(int k=2;k<=j;k++)
if(c[k]^c[k-1]){
d2[D++]+=k-lst;
lst=k;
}
mx=max(mx,(ll)D-1);
}
for(int i=1;i<=mx;i++)
ans1+=max(d1[i]-1,(ll)0);
for(int i=1;i<=mx;i++)
ans2+=max(d2[i]-1,(ll)0);
write(max(ans1,ans2));
return 0;
}
本文作者:luckydrawbox
本文链接:https://www.cnblogs.com/luckydrawbox/p/18526569
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
分类:
题解
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步