题解 P8001
HYdroKomide · · 题解
题意:
题目里说的挺简洁明白的,换句话说也可以是最小化相邻字符不同的个数。
很明显,这个也可以理解成:每次取所有串前面一样的数,使取的次数最少。
思路:
首先,取的方法决定,该取一个数就一定要把这一个串前面的这个数全部取出来,所以一个串取的次数最少就是相邻字符不同的个数再
每次要把所有的串前面的数都取出来,所以每个串取的次数都应该考虑。整体能够取的次数就是所有串能取次数的最大值。
然后就出来一份代码:
#include<iostream>
#include<cstring>
#define ri register int
using namespace std;
int n,l,tot,cnt,maxcnt;
string s;
int main(){
ios::sync_with_stdio(false);
cin>>n;
for(ri i=1;i<=n;i++){
cin>>s;
l=s.length(),cnt=0;
tot+=l;//一共相邻的字符数,就是全部字符的个数-1
for(ri j=1;j<l;j++)
if(s[j]!=s[j-1])//求相邻字符不同的个数
cnt++;
maxcnt=cnt>maxcnt?cnt:maxcnt;//取最大值
}
tot--;
cout<<tot-maxcnt<<endl;//最后减去不同的个数
return 0;
}
然而只有 50pts。
原因应该很明显,一个串的开头可能是
所以我们对于每个串,都同时考虑最先取
程序如下:
#include<iostream>
#include<cstring>
#define ri register int
using namespace std;
int n,l,tot,cnt0,cnt1,maxcnt0,maxcnt1,maxcnt;
string s;
int main(){
ios::sync_with_stdio(false);
cin>>n;
for(ri i=1;i<=n;i++){
cin>>s;
l=s.length(),cnt0=cnt1=0;
tot+=l;
if(s[0]=='0')cnt1++;//如果字符串开头是0,那么一开始取1的次数+1
if(s[0]=='1')cnt0++;//反之亦然
for(ri j=1;j<l;j++)
if(s[j]!=s[j-1])
cnt0++,cnt1++;
maxcnt0=cnt0>maxcnt0?cnt0:maxcnt0;
maxcnt1=cnt1>maxcnt1?cnt1:maxcnt1;
}
maxcnt=min(maxcnt0,maxcnt1);//取其最小值
tot--;
cout<<tot-maxcnt<<endl;
return 0;
}