zoukankan      html  css  js  c++  java
  • Codeforces 1071 C

    C - Triple Flips

    思路:

    小范围暴力

    大范围递归构造

    构造方法:

    solve(l, r) 表示使l 到 r 区间全变为0的方法

    为了使反转次数小于等于n/3 + 12

    我们只需要保证每次反转后区间长度减少值的期望为3就可以了

    如果a[l] == 0, l++

    如果a[r] == 0, r--

    如果a[l] == 1 && a[l+1] == 1 && a[l+2] == 1, 反转这三个就可以啦, l += 3

    如果a[l] == 1 && a[l+1] == 0 && a[l+2] == 1, 反转l, l+2, l+4这三个, l += 3

    如果a[l] == 1 && a[l+1] == 0 && a[l+1] == 0, 反转l, l+3, l+6这三个, l += 3

    从右区间减少同理

    否则只剩下这种情况了:

    1 1 0 ...... 0 1 1

    那么只需要根据区间长度的奇偶性

    反转l , (l+r)/2, r 和 l+1 , (l+1+r-1)/2, r-1 或者 l, (l+r-1)/2, r-1 和 l+1 , (l+1+r)/2, r 

    然后 l += 3, r -= 3, 区间长度减少6

    区间长度小于8的话就暴力

    用二进制枚举所有的反转情况, 然后检查

    代码:

    #pragma GCC optimize(2)
    #pragma GCC optimize(3)
    #pragma GCC optimize(4)
    #include<bits/stdc++.h>
    using namespace std;
    #define fi first
    #define se second
    #define pi acos(-1.0)
    #define LL long long
    //#define mp make_pair
    #define pb push_back
    #define ls rt<<1, l, m
    #define rs rt<<1|1, m+1, r
    #define ULL unsigned LL
    #define pll pair<LL, LL>
    #define pli pair<LL, int>
    #define pii pair<int, int>
    #define piii pair<pii, int>
    #define mem(a, b) memset(a, b, sizeof(a))
    #define fio ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
    #define fopen freopen("in.txt", "r", stdin);freopen("out.txt", "w", stout);
    //head
    
    #define ck(l, x, y, z) a[l]==x&&a[l+1]==y&&a[l+2]==z
    #define ckk(r, x, y, z) a[r]==x&&a[r-1]==y&&a[r-2]==z
    const int N = 1e5 + 10;
    int a[N], tmp[N], n;
    vector<piii> ans;
    bool f = false;
    void flip(int x, int y, int z) {
        a[x] ^= 1;
        a[y] ^= 1;
        a[z] ^= 1;
        ans.pb({{x, y}, z});
    }
    void fflip(int x, int y) {
        a[x] ^= 1;
        a[x+y>>1] ^= 1;
        a[y] ^= 1;
        ans.pb({{x, x+y>>1}, y});
    }
    void Flip(int x, int y) {
        tmp[x] ^= 1;
        tmp[x+y>>1] ^= 1;
        tmp[y] ^= 1;
        //ans.pb({{x, x+y>>1}, y});
    }
    void bruteforce(int l, int r) {
        vector<pii> vc;
        for (int i = l; i <= r; i++) {
            for (int j = i+2; j <= r; j += 2) {
                vc.pb({i, j});
            }
        }
        int sz = vc.size();
        for (int i = 0; i < (1<<sz); i++) {
            for (int j = l; j <= r; j++) tmp[j] = a[j];
            for (int j = 0; j < sz; j++) {
                if(i&(1<<j)) {
                    Flip(vc[j].fi, vc[j].se);
                }
            }
            bool ff = true;
            for (int j = l; j <= r; j++) if(tmp[j]) {ff = false; break;}
            if(ff) {
                f = true;
                for (int j = 0; j < sz; j++) if(i&(1<<j))ans.pb({{vc[j].fi, vc[j].fi + vc[j].se >> 1}, vc[j].se});
                return ;
            }
        }
    }
    void solve(int l, int r) {
        if(r - l + 1 <= 8) {
            while(r-l+1 < 8 && l > 1) l--;
            while(r-l+1 < 8 && r < n) r++;
            bruteforce(l, r);
            return ;
        }
        if(a[l] == 0) {
            solve(l+1, r);
            return ;
        }
        if(a[r] == 0) {
            solve(l, r-1);
            return ;
        }
        if(ck(l, 1, 1, 1)) {
            flip(l, l+1, l+2);
            solve(l+3, r);
            return ;
        }
        if(ck(l, 1, 0, 1)) {
            flip(l, l+2, l+4);
            solve(l+3, r);
            return ;
        }
        if(ck(l, 1, 0, 0)) {
            flip(l, l+3, l+6);
            solve(l+3, r);
            return ;
        }
        if(ckk(r, 1, 1, 1)) {
            flip(r, r-1, r-2);
            solve(l, r-3);
            return ;
        }
        if(ckk(r, 1, 0, 1)) {
            flip(r, r-2, r-4);
            solve(l, r-3);
            return ;
        }
        if(ckk(r, 1, 0, 0)) {
            flip(r, r-3, r-6);
            solve(l, r-3);
            return ;
        }
        if((r-l+1)&1) {
            fflip(l, r);
            fflip(l+1, r-1);
            solve(l+3, r-3);
            return ;
        }
        else {
            fflip(l, r-1);
            fflip(l+1, r);
            solve(l+3, r-3);
            return ;
        }
    }
    int main() {
        int cnt = 0;
        scanf("%d", &n);
        for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
        solve(1, n);
        if(f) {
            printf("YES
    ");
            printf("%d
    ", (int)ans.size());
            for (piii p : ans) printf("%d %d %d
    ", p.fi.fi, p.fi.se, p.se);
        }
        else printf("NO
    ");
        return 0;
    }
  • 相关阅读:
    对NumPy中dot()函数的理解
    使用Boostrap框架写一个登录注册界面
    两种方法实现asp.net方案的前后端数据交互(aspx文件、html+ashx+ajax)
    将包含经纬度点位信息的Excel表格数据导入到ArcMap中并输出成shapefile
    [ArcGIS API for JavaScript 4.8] Sample Code-Popups-1-popupTemplate的概念和popup中属性字段值的多种表现形式
    [python爬虫]Requests-BeautifulSoup-Re库方案--robots协议与Requests库实战
    [python爬虫]Requests-BeautifulSoup-Re库方案--Requests库介绍
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-widgets简介
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-popups简介
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-layers简介
  • 原文地址:https://www.cnblogs.com/widsom/p/9964761.html
Copyright © 2011-2022 走看看