CF660C Hard Process(尺取法)

整理的算法模板合集: ACM模板


在这里插入图片描述
尺取法

题目中要我们求最多改变k次后连续的1的最长长度。那么转换一下,不就是求至多包含k个0的子串的最长长度吗?
直接套用尺取法的思想,维护两端点,一旦0的个数超过k左端点就右移一位(要用if而不是while,不然会RE,因为一位就够了,最后的答案也不会出错)

#include<cstdio>
#include<algorithm>
#include<cstring>
#include<iostream>
#include<queue>
using namespace std;
typedef long long ll;
typedef pair<int, int> PII ;
const int N = 500007, M = 5000007, INF = 0x3f3f3f3f;

int n, m, k;
int a[N];
int main()
{
    scanf("%d%d", &n, &k);
    for(int i = 1;i <= n; ++ i){
        scanf("%d", &a[i]);
    }
    int l = 1, r = 1;
    int cnt = 0;
    int maxv = 0, ml, mr, ans = 0;
    //维护一个区间,使得区间内的0的个数不超过k个的最长区间长度
    for(int r = 1; r <= n; ++ r){
        cnt += !a[r];
        maxv += 1;
        if(cnt > k){
            cnt -= !a[l];
            l ++ ;
            maxv -= 1;
        }
        if(maxv > ans){
            ans = maxv, ml = l, mr = r;
        }
    }
    printf("%d\n", ans);
    for(int i = ml; i <= mr ; ++ i)a[i] = 1;
    for(int i = 1; i <= n; ++ i)
        printf("%d ",a[i]);
    return 0;
}

©️2020 CSDN 皮肤主题: 酷酷鲨 设计师:CSDN官方博客 返回首页