「日常训练」Alternative Thinking(Codeforces Round #334 Div.2 C)
题意与分析 (CodeForces - 603A)
这题真的做的我头疼的不得了,各种构造样例去分析性质。。。
题意是这样的:给出01字符串。可以在这个字符串中选择一个起点和一个终点使得这个连续区间内所有的位取反。求经过处理后最多会得到多少次01变换(可以不连续)。
首先求原串的最长01长度,这个太简单了,然后才是重头戏:精彩的构造样例分类讨论环节——如何增加01的最长串?
我们考虑一下反转串的几种情况:1、反转单个连续0/1串的内部;2、反转两个部分连续0/1串与中间的内容(内部无连续串)3、反转两个部分连续0/1串与中间的内容(内部有连续串)4、反转连续01串(不是0/1串!)
第一种情况是最好考虑的,不论你是1000..0001还是0111...11110,里面不论怎么反转,最后对答案的贡献也多一个01/10,也就是2。这种多的贡献仅仅出现在0/1串长度大于等于三的情况。
第二种情况稍微复杂一些:先考虑0开头的情况,也就是00..0{101010101}1..11或者00..0{101010101}0..00。这种情况下最好的处理是连着前后一个字符一起反转:00..1{010101010}0..11于是长度喜多2。这种情况下,前面跟着一个串(长度大于等于2即可)就产生1的贡献,后面跟着一个就产生一个贡献。1开头的同理。
第三种情况建立在2的基础上:如果反转串中间也有连续会怎样?什么时期都不会发生,因为它作出的贡献仅仅相当于一个单个字符。于是答案同2。
第四种情况比较有趣了:我对原答案做反转,没有连续的01会怎样?那你不管怎么样,最优答案总是原先的最长长度。
综合以上四种情况,我们可以得到这个结论:
如果整个串里面的00/11串个数\(\le 2\),那么答案(即原先长度)加上这个串的个数;否则答案最多+2。情况1此时已经被包括在内了,因为长度为3的连续串一定有两个00/11串。
代码
/*
* Filename: cfr334d2c.cpp
* Date: 2018-11-05
*/
#include <bits/stdc++.h>
#define INF 0x3f3f3f3f
#define PB emplace_back
#define MP make_pair
#define fi first
#define se second
#define rep(i,a,b) for(repType i=(a); i<=(b); ++i)
#define per(i,a,b) for(repType i=(a); i>=(b); --i)
#define ZERO(x) memset(x, 0, sizeof(x))
#define MS(x,y) memset(x, y, sizeof(x))
#define ALL(x) (x).begin(), (x).end()
#define QUICKIO \
ios::sync_with_stdio(false); \
cin.tie(0); \
cout.tie(0);
#define DEBUG(...) fprintf(stderr, __VA_ARGS__), fflush(stderr)
using namespace std;
using pi=pair<int,int>;
using repType=int;
using ll=long long;
using ld=long double;
using ull=unsigned long long;
int dp[100005][2];
int
main()
{
int n; cin>>n;
bool b[100005];
string str; cin>>str;
int maxlen=0,nowlen=0;
bool last;
int cnt=0;
rep(i,0,n-1)
{
b[i+1]=str[i]=='0';
if(i==0)
{
dp[i+1][0]=str[i]=='0';
dp[i+1][1]=str[i]=='1';
last=b[i+1];
nowlen=1;
}
else
{
if(last==b[i+1])
{
nowlen++;
maxlen=max(nowlen,maxlen);
}
else
{
cnt+=nowlen-1;
nowlen=1;
last=b[i+1];
}
if(str[i]=='0')
{
dp[i+1][1]=dp[i][1];
dp[i+1][0]=dp[i][1]+1;
}
else
{
dp[i+1][1]=dp[i][0]+1;
dp[i+1][0]=dp[i][0];
}
}
}
if(nowlen!=1) cnt+=nowlen-1;
int ans=0;
rep(i,1,n)
ans=max(ans,max(dp[i][0],dp[i][1]));
/*
rep(i,1,n)
cout<<dp[i][0]<<" ";
cout<<endl;
rep(i,1,n)
cout<<dp[i][1]<<" ";
cout<<endl;
*/
cout<<ans+min(2,cnt)<<endl;
return 0;
}
「日常训练」Alternative Thinking(Codeforces Round #334 Div.2 C)的更多相关文章
- 「日常训练」ZgukistringZ(Codeforces Round #307 Div. 2 B)
题意与分析(CodeForces 551B) 这他妈哪里是日常训练,这是日常弟中弟. 题意是这样的,给出一个字符串A,再给出两个字符串B,C,求A中任意量字符交换后(不限制次数)能够得到的使B,C作为 ...
- 「日常训练」Queue(Codeforces Round 303 Div.2 D)
简单到让人不敢相信是D题,但是还是疏忽了一点. 题意与分析 (Codeforces 545D) 题意:n人排队,当一个人排队的时间超过他需要服务的时间就会厌烦,现在要求一个最优排列使得厌烦的人最少. ...
- 「日常训练」Woodcutters(Codeforces Round 303 Div.2 C)
这题惨遭被卡..卡了一个小时,太真实了. 题意与分析 (Codeforces 545C) 题意:给定\(n\)棵树,在\(x\)位置,高为\(h\),然后可以左倒右倒,然后倒下去会占据\([x-h,x ...
- 「日常训练」Skills(Codeforce Round #339 Div.2 D)
题意(CodeForces 614D) 每个人有\(n(n\le 10^5)\)个技能,技能等级都在\([0,10^9]\)的范围,每个技能有一个当前等级,所有技能的最高等级都为A.一个人的力量被记做 ...
- 「专题训练」k-Tree(CodeForces Round #247 Div.2 C)
题意与分析(Codeforces-431C) 题意是这样的:给出K-Tree--一个无限增长的树,它的每个结点都恰有\(K\)个孩子,每个节点到它\(K\)个孩子的\(K\)条边的权重各为\(1,2, ...
- 「专题训练」Boredom(CodeForces Round #260 Div.1 A)
题意(Codeforces-455A) 给你\(n\)个数,你每次可以选择删除去一个数\(x\)获得\(x\)分,但是所有为\(x+1\)和\(x-1\)的数都得删去.问最大获得分数. 分析 这是一条 ...
- Codeforces Round #334 (Div. 2) A. Uncowed Forces 水题
A. Uncowed Forces Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/contest/604/pro ...
- 「日常训练」Watering Flowers(Codeforces Round #340 Div.2 C)
题意与分析 (CodeForces 617C) 题意是这样的:一个花圃中有若干花和两个喷泉,你可以调节水的压力使得两个喷泉各自分别以\(r_1\)和\(r_2\)为最远距离向外喷水.你需要调整\(r_ ...
- 「日常训练」More Cowbell(Codeforces Round #334 Div.2 B)
题意与分析(CodeForces 604B) 题意是这样的:\(n\)个数字,\(k\)个盒子,把\(n\)个数放入\(k\)个盒子中,每个盒子最多只能放两个数字,问盒子容量的最小值是多少(水题) 不 ...
随机推荐
- 原生JS写验证码
1.先创建一个一个输入框用来用户输入验证码和一个span容器用来存放系统给出的验证码和一个刷新按钮还有一个登录按钮 <input type="text" class=&quo ...
- 查找连接过的USB存储设备
gp "HKLM:\SYSTEM\CurrentControlSet\Enum\USBSTOR\*\*"|select friendlyname,CompatibleIDs,mfg ...
- 2019.1.2 Spring管理事务的方式
Spring管理事务的方式 1.编码式 1.将核心事务管理器配置到Spring容器 2.配置TransactionTemplate模版 3.将事务模版注入service 4.在Service中调用模版 ...
- x+=i和x = x+i比较 -- 简单赋值和复合赋值
这两个赋值方式其实是有区别的,如果最后结果的类型和左操作数的类型一样,那么这两个表达式就完全等价. 下面来看看两个例子来理解它们的区别: 编写一个程序,使得x+=i合法, x = x+i: 不合法. ...
- Python嵌套列表去重
raw_list = [ [ 'CS_SUPP_INFO', 'A', '1'], [ 'CS_SUPP_INFO', '1', 'A'], [ 'CS_SUPP_INFO', '1', 'A'], ...
- oracle 优化相关
--选择最有效率的表名顺序: Oracle的解析器按照从右到左的顺序处理FROM子句中的表名,FROM子句中写在最后的表(基础表 driving table)将被最先处理, 在FROM子句中包含多 ...
- 一个 Safari 的 new Date() bug
开发「bufpay.com 个人即时到账收款平台」后台套餐修改功能的时候碰到一个 new Date() bug. 既在 Safari 里面不支持 var t = new Date('2018-06-1 ...
- CSS实现图片等比例缩小不变形
<img src="../images/bg1.jpg" alt="" /> img { /*等宽缩小不变形*/ /*width: 100%;*/ ...
- axios和ajax,fetch的区别
1,传统 Ajax 指的是 XMLHttpRequest(XHR), 最早出现的发送后端请求技术,隶属于原始js中,核心使用XMLHttpRequest对象,多个请求之间如果有先后关系的话,就会出现回 ...
- SQL语言简单总结
常用的Sql语言总结: 1. create datebase datebaseName //创建数据库 2. drop datebase datebaseName // ...