D - Handstand


Time Limit: 2 sec / Memory Limit: 1024 MB

Score : 400400 points

Problem Statement

NN people are arranged in a row from left to right.

You are given a string SS of length NN consisting of 0 and 1, and a positive integer KK.

The ii-th person from the left is standing on feet if the ii-th character of SS is 0, and standing on hands if that character is 1.

You will give the following direction at most KK times (possibly zero):

Direction: Choose integers ll and rr satisfying 1≤l≤r≤N1≤l≤r≤N, and flip the ll-th, (l+1)(l+1)-th, ......, and rr-th persons. That is, for each i=l,l+1,...,ri=l,l+1,...,r, the ii-th person from the left now stands on hands if he/she was standing on feet, and stands on feet if he/she was standing on hands.

Find the maximum possible number of consecutive people standing on hands after at most KK directions.

Constraints

  • NN is an integer satisfying 1≤N≤1051≤N≤105.
  • KK is an integer satisfying 1≤K≤1051≤K≤105.
  • The length of the string SS is NN.
  • Each character of the string SS is 0 or 1.

Input

Input is given from Standard Input in the following format:

NN KK
SS

Output

Print the maximum possible number of consecutive people standing on hands after at most KK directions.


Sample Input 1 Copy

Copy
5 1
00010

Sample Output 1 Copy

Copy
4

We can have four consecutive people standing on hands, which is the maximum result, by giving the following direction:

  • Give the direction with l=1,r=3l=1,r=3, which flips the first, second and third persons from the left.

Sample Input 2 Copy

Copy
14 2
11101010110011

Sample Output 2 Copy

Copy
8

Sample Input 3 Copy

Copy
1 1
1

Sample Output 3 Copy

Copy
1

No directions are necessary.

题意:

给你一个只含有0和1的字符串,并且给你一个数字K,你可以选择最多K次区间,每一个区间L<=R,然后对这个区间的元素进行取反操作。

即0变成1,1变成0,问你在最聪明的操作之后最大可以获得的连续1的串是多长?

可以看样例解释理解题意。

思路:

我们对字符串的连续1和0串进行计数处理,即把连续的1或者0的个数记录起来,

那么字符串会生成如下的数组

例如字符串是  110000111001101

我们把连续的1和连续0分别放入a和b数组,

那么a的元素是2 3 2 1

b的元素是4 2 1

我们思考可以发现,我们想要最长的连续1串,那么我们处理的区间肯定是连续的0区间,让他们变成1,然后来增长连续1串的长度。

即处理的0区间一定是连续的。

那么我们可以知道如下,例如我们处理两个区间,那么可以的得到的最长的连续1串就是这两个区间的0串长度的sum和以及这两个0串前后和中间的1串的sum和。

那么我们只需要枚举连续的K个的0串即可,

细节见代码:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <vector>
#include <iomanip>
#define ALL(x) (x).begin(), (x).end()
#define rt return
#define dll(x) scanf("%I64d",&x)
#define xll(x) printf("%I64d\n",x)
#define sz(a) int(a.size())
#define all(a) a.begin(), a.end()
#define rep(i,x,n) for(int i=x;i<n;i++)
#define repd(i,x,n) for(int i=x;i<=n;i++)
#define pii pair<int,int>
#define pll pair<long long ,long long>
#define gbtb ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define MS0(X) memset((X), 0, sizeof((X)))
#define MSC0(X) memset((X), '\0', sizeof((X)))
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define eps 1e-6
#define gg(x) getInt(&x)
#define db(x) cout<<"== [ "<<x<<" ] =="<<endl;
using namespace std;
typedef long long ll;
ll gcd(ll a,ll b){return b?gcd(b,a%b):a;}
ll lcm(ll a,ll b){return a/gcd(a,b)*b;}
ll powmod(ll a,ll b,ll MOD){ll ans=;while(b){if(b%)ans=ans*a%MOD;a=a*a%MOD;b/=;}return ans;}
inline void getInt(int* p);
const int maxn=;
const int inf=0x3f3f3f3f;
/*** TEMPLATE CODE * * STARTS HERE ***/
int n;
int k;
char s[maxn];
std::vector<int> v1,v2;
ll sum1[maxn];
ll sum2[maxn];
int main()
{
//freopen("D:\\common_text\\code_stream\\in.txt","r",stdin);
//freopen("D:\\common_text\\code_stream\\out.txt","w",stdout);
gbtb;
cin>>n>>k;
cin>>s;
int cnt=;
// int i=0;
if(s[]=='')
{
v1.pb();
}
repd(i,,n-)
{
if(s[i]=='')
{
while(s[i]=='')
{
cnt++;
i++;
}
v2.push_back(cnt);
cnt=;
i--;
}
if(s[i]=='')
{
while(s[i]=='')
{
cnt++;
i++;
}
v1.push_back(cnt);
cnt=;
i--;
} }
int num=max(sz(v1),sz(v2));
repd(i,,maxn-)
{
v1.push_back();
v2.push_back();
}
repd(i,,maxn-)
{
sum1[i]+=sum1[i-]+v1[i-];
sum2[i]+=sum2[i-]+v2[i-];
}
int w=;
ll ans=0ll;
repd(i,,n-k+)
{
int l=i;
int r=l+k;
ll temp=sum1[r]-sum1[l-];
temp+=sum2[r-]-sum2[l-];
ans=max(ans,temp);
}
cout<<ans<<endl; return ;
} inline void getInt(int* p) {
char ch;
do {
ch = getchar();
} while (ch == ' ' || ch == '\n');
if (ch == '-') {
*p = -(getchar() - '');
while ((ch = getchar()) >= '' && ch <= '') {
*p = *p * - ch + '';
}
}
else {
*p = ch - '';
while ((ch = getchar()) >= '' && ch <= '') {
*p = *p * + ch - '';
}
}
}

AtCoder Beginner Contest 124 D - Handstand(思维+前缀和)的更多相关文章

  1. AtCoder Beginner Contest 249 E - RLE // 动态规划 + 前缀和优化

    传送门:E - RLE (atcoder.jp) 题意: 求满足原长为N且转换后长度严格小于N条件的小写字母组成的字符串的数量,输出时对P取模. 其中,转换规则为,将连续相同的字串替换为"字 ...

  2. Atcoder Beginner Contest 124 解题报告

    心态爆炸.本来能全做出来的.但是由于双开了Comet oj一个比赛,写了ABC就去搞那个的B题 还被搞死了. 回来写了一会D就过了.可惜比赛已经结束了.真的是作死. A - Buttons #incl ...

  3. AtCoder Beginner Contest 188 F - +1-1x2 思维题

    题目描述 给你两个数 \(x\),\(y\) 可以对 \(x\) 进行 \(+1,-1\) 或 \(\times 2\) 的操作 问最少操作多少次后变为 \(y\) \(x,y \leq 10^{18 ...

  4. AtCoder Beginner Contest 176 E - Bomber (思维)

    题意:有一张\(H\)x\(W\)的图,给你\(M\)个目标的位置,你可以在图中放置一枚炸弹,炸弹可以摧毁所在的那一行和一列,问最多可以摧毁多少目标. 题解:首先我们记录某一行和某一列目标最多的数目, ...

  5. AtCoder Beginner Contest 154 题解

    人生第一场 AtCoder,纪念一下 话说年后的 AtCoder 比赛怎么这么少啊(大雾 AtCoder Beginner Contest 154 题解 A - Remaining Balls We ...

  6. AtCoder Beginner Contest 177 题解

    AtCoder Beginner Contest 177 题解 目录 AtCoder Beginner Contest 177 题解 A - Don't be late B - Substring C ...

  7. KYOCERA Programming Contest 2021(AtCoder Beginner Contest 200) 题解

    KYOCERA Programming Contest 2021(AtCoder Beginner Contest 200) 题解 哦淦我已经菜到被ABC吊打了. A - Century 首先把当前年 ...

  8. AtCoder Beginner Contest 100 2018/06/16

    A - Happy Birthday! Time limit : 2sec / Memory limit : 1000MB Score: 100 points Problem Statement E8 ...

  9. AtCoder Beginner Contest 052

    没看到Beginner,然后就做啊做,发现A,B太简单了...然后想想做完算了..没想到C卡了一下,然后还是做出来了.D的话瞎想了一下,然后感觉也没问题.假装all kill.2333 AtCoder ...

随机推荐

  1. 用javaweb连接数据库用javabean、severlet实现增删改查

    样 很重要的一点是建立数据库的连接 数据库是一切操作的前提 不管是增加 删除 修改 查询 都需要调用数据库连接程序 再就是java的类的编写  写完类后需要对其进行增删改查方法的 编写 这是dao层的 ...

  2. Java多线程之---用 CountDownLatch 说明 AQS 的实现原理

    本文基于 jdk 1.8 . CountDownLatch 的使用 前面的文章中说到了 volatile 以及用 volatile 来实现自旋锁,例如 java.util.concurrent.ato ...

  3. tar -P参数含义

    -p(小写) :保留备份数据的原本权限与属性,常用于备份(-c) 重要的配置文件-P(大写) :保留绝对路径,亦即允许备份数据中含有根目录存在之意: 在加上绝对路径出现的那个警告讯息“tar: Rem ...

  4. NET Core应用中使用缓存

    NET Core应用中使用缓存 .NET Core针对缓存提供了很好的支持 ,我们不仅可以选择将数据缓存在应用进程自身的内存中,还可以采用分布式的形式将缓存数据存储在一个“中心数据库”中.对于分布式缓 ...

  5. Numpy常用概念-对象的副本和视图、向量化、广播机制

    一.引言 在我们操作数组的时候,返回的是新数组还是原数组的链接,我们就需要了解对象副本和视图的区别. 向量化和广播是numpy内部实现的基础. 二.对象副本和视图 我们应该注意到,在操作数组的时候返回 ...

  6. 【面向对象设计原则】之单一职责原则(SRP)

    单一职责原则是面向对象原则五大原则中最简单,也是最重要的一个原则, 他的字面定义如下: 单一职责原则(Single Responsibility Principle, SRP): 一个类只负责一个功能 ...

  7. idea部署Maven入门(一)——环境变量的配置和下载

        介绍:       1  Maven是用来管理jar包的一种工具,       2  Maven主要是构建java项目和java web项目        3 maven项目管理所依赖的jar ...

  8. SpringMVC从认识到细化了解

    目录 SpringMVC的介绍 介绍: 执行流程 与strut2的对比 基本运行环境搭建 基础示例 控制器的编写 控制器创建方式: 请求映射问题: 获取请求提交的参数 通过域对象(request,re ...

  9. Javascript数组系列五之增删改和强大的 splice()

    今天是我们介绍数组系列文章的第五篇,也是我们数组系列的最后一篇文章,只是数据系列的结束,所以大家不用担心,我们会持续的更新干货文章. 生命不息,更新不止! 今天我们就不那么多废话了,直接干货开始. 我 ...

  10. asp.net core自定义端口

    asp.net Core 自定义端口 官方文档 aspnet内库源码: https://github.com/aspnet dotnet系统内库源码:https://github.com/dotnet ...