結果

問題 No.5002 stick xor
ユーザー sumorusumoru
提出日時 2018-05-26 18:25:35
言語 C++17
(gcc 12.3.0 + boost 1.83.0)
結果
AC  
実行時間 945 ms / 1,000 ms
コード長 6,306 bytes
コンパイル時間 33,665 ms
実行使用メモリ 1,604 KB
スコア 43,123
最終ジャッジ日時 2018-05-26 18:26:10
ジャッジサーバーID
(参考情報)
judge6 /
純コード判定しない問題か言語
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 936 ms
1,600 KB
testcase_01 AC 941 ms
1,604 KB
testcase_02 AC 939 ms
1,600 KB
testcase_03 AC 938 ms
1,604 KB
testcase_04 AC 940 ms
1,604 KB
testcase_05 AC 944 ms
1,604 KB
testcase_06 AC 942 ms
1,600 KB
testcase_07 AC 939 ms
1,600 KB
testcase_08 AC 940 ms
1,600 KB
testcase_09 AC 936 ms
1,600 KB
testcase_10 AC 938 ms
1,600 KB
testcase_11 AC 936 ms
1,604 KB
testcase_12 AC 937 ms
1,600 KB
testcase_13 AC 940 ms
1,604 KB
testcase_14 AC 936 ms
1,600 KB
testcase_15 AC 945 ms
1,600 KB
testcase_16 AC 934 ms
1,600 KB
testcase_17 AC 935 ms
1,604 KB
testcase_18 AC 942 ms
1,604 KB
testcase_19 AC 939 ms
1,600 KB
testcase_20 AC 941 ms
1,600 KB
testcase_21 AC 938 ms
1,600 KB
testcase_22 AC 941 ms
1,600 KB
testcase_23 AC 938 ms
1,604 KB
testcase_24 AC 939 ms
1,604 KB
testcase_25 AC 942 ms
1,600 KB
testcase_26 AC 938 ms
1,600 KB
testcase_27 AC 937 ms
1,604 KB
testcase_28 AC 936 ms
1,604 KB
testcase_29 AC 942 ms
1,604 KB
testcase_30 AC 936 ms
1,600 KB
testcase_31 AC 942 ms
1,600 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

#include<algorithm>
#include<cmath>
#include<iomanip>
#include<iostream>
#include<map>
#include<numeric>
#include<queue>
#include<set>
#include<sstream>
#include<unordered_map>
#include<unordered_set>
#include<vector>
#include<random>
#include<sys/time.h>
using ll = long long;
enum : int { M = (int)1e9 + 7 };
enum : ll { MLL = (ll)1e18L + 9 };
using namespace std;
#ifdef LOCAL
#include"rprint2.hpp"
#include"debug_deque.hpp"
#define vector DebugDeque
#else
#define FUNC(name) template <ostream& out = cout, class... T> void name(T&&...){ }
FUNC(prints) FUNC(printe) FUNC(printw) FUNC(printew) FUNC(printb) FUNC(printd) FUNC(printde);
#endif
template <class S, class T>
istream& operator >> (istream& in, pair<S, T>& p){ in >> p.first >> p.second; return in; }
template <class T>
istream& operator >> (istream& in, vector<T>& v){ for(auto& e : v){ in >> e; } return in; }

#define LIMIT 0.9
mt19937 mt;
timeval start;
double elapsed(){
    timeval now;
    gettimeofday(&now, nullptr);
    return (now.tv_sec - start.tv_sec) + (now.tv_usec - start.tv_usec) / 1e6;
}

struct Ans {
    int a, b, c, d;
    friend ostream& operator << (ostream& out, Ans& e) {
        return out << e.a + 1 << ' ' << e.b + 1 << ' ' << e.c + 1 << ' ' << e.d + 1;
    }
    bool operator < (const Ans&) const { return false; }
};

int main(){
    gettimeofday(&start, nullptr);
    cin.tie(0);
    ios::sync_with_stdio(false);
    int n, k;
    cin >> n >> k;
    vector<int> ls(k); cin >> ls;
    vector<string> as(n); cin >> as;
    for(auto& a : as){ for(auto& e : a){ e -= '0'; } }
    auto as0 = as;
    auto calc = [&](){ 
        int num = 0;
        for(int i = 0; i < n; i++){ for(int j = 0; j < n; j++){
            num += as[i][j];
        } }
        return num;
    };
    int score0 = calc();
    vector<Ans> ans(k);
    // vector<pair<int, int>> ps(k);
    // for(int i = 0; i < k; i++){
    //     ps[i] = {ls[i], i};
    // }
    // sort(ps.rbegin(), ps.rend());
    // for(auto p : ps){
    //     int i = p.second;

    auto rev = [](auto& e){ 
        e = !e;
    };
    auto put = [&](Ans a){ 
        int ret = 0;
        for(int y = a.a; y <= a.c; y++){
            for(int x = a.b; x <= a.d; x++){
                rev(as[y][x]);
                ret += as[y][x] * 2 - 1;
            }
        }
        return ret;
    };
    auto findBest = [&](int l){ 
        pair<int, Ans> ret(-1, {});
        for(int y = 0; y < n; y++){
            for(int x = 0; x < n - l; x++){
                pair<int, Ans> cand(0, {y, x, y, x + l - 1});
                for(int j = 0; j < l; j++){
                    cand.first += as[y][x + j];
                }
                ret = max(ret, cand);
            }
        }
        for(int y = 0; y < n - l; y++){
            for(int x = 0; x < n; x++){
                pair<int, Ans> cand(0, {y, x, y + l - 1, x});
                for(int j = 0; j < l; j++){
                    cand.first += as[y + j][x];
                }
                ret = max(ret, cand);
            }
        }
        return ret;
    };

        // for(int i = 0; i < k; i++){
        //     put(ans[i] = findBest(ls[i]).second);
        // }
        // printde(score0 - calc());
    int maxi = 0;
    auto as1 = as;
    auto ans1 = ans;
    vector<int> is, is2;
    int thre = 6;
    for(int i = 0; i < k; i++){
        (ls[i] > thre ? is : is2).push_back(i);
    }
    // vector<int> is(k); iota(is.begin(), is.end(), 0);
    for(int _ = 0; _ < 10; _++){
        as = as0;
        for(auto i : is){
            put(ans[i] = findBest(ls[i]).second);
        }
        int cand = score0 - calc();
        if(maxi < cand){
            maxi = cand;
            ans1 = ans;
            as1 = as;
        }
        printde(cand);
        shuffle(is.begin(), is.end(), mt);
    }
    as = as1;
    ans = ans1;

    while(elapsed() < LIMIT){ for(int _ = 0; _ < 100; _++){
    // for(elapsed() < LIMIT){ for(int i = 0; i < 100; i++){
        int i = mt() % k;
        if(ls[i] <= thre){ continue; }
        auto& a = ans[i];
        put(a);
        a = findBest(ls[i]).second;
        put(a);
        if(a.a == a.c){
            if(a.d + 1 < n && as[a.a][a.b] && as[a.a][a.d + 1]){
                rev(as[a.a][a.b]);
                rev(as[a.a][a.d + 1]);
                a.b++; a.d++;
            }
            if(a.b && as[a.a][a.b - 1] && as[a.a][a.d]){
                rev(as[a.a][a.b - 1]);
                rev(as[a.a][a.d]);
                a.b--; a.d--;
            }
        }
        if(a.b == a.d){
            if(a.c + 1 < n && as[a.a][a.b] && as[a.c + 1][a.b]){
                rev(as[a.a][a.b]);
                rev(as[a.c + 1][a.b]);
                a.a++; a.c++;
            }
            if(a.a && as[a.a - 1][a.b] && as[a.c][a.b]){
                rev(as[a.a - 1][a.b]);
                rev(as[a.c][a.b]);
                a.a--; a.c--;
            }
        }
    } }

    // vector<pair<double, int>> rs;
    // for(int i = 0; i < k; i++){
    //     int cnt = 0;
    //     for(int y = ans[i].a; y <= ans[i].c; y++){
    //         for(int x = ans[i].b; x <= ans[i].d; x++){
    //             cnt += as[y][x];
    //         }
    //     }
    //     rs.emplace_back(1. * cnt / ls[i], i);
    // }
    // sort(rs.rbegin(), rs.rend());
    // for(int i = 0; i < 10; i++){
    //     printe(rs[i].first, ls[rs[i].first]);
    // }
    int score = score0 - calc();
    printde(score);
    // vector<pair<int, int>> ps;
    // for(auto i : is2){
    //     ps.emplace_back(ls[i], i);
    // }
    // sort(ps.rbegin(), ps.rend());
    // for(auto& p : ps){
    //     put(ans[p.second] = findBest(p.first).second);
    // }

    // for(auto i : is2){
    //     put(ans[i] = findBest(ls[i]).second);
    // }
    // score = score0 - calc();
    // printde(score);

    as0 = as;
    maxi = 0;
    for(int _ = 0; _ < 10; _++){
        as = as0;
        for(auto i : is2){
            put(ans[i] = findBest(ls[i]).second);
        }
        int cand = score0 - calc();
        if(maxi < cand){
            maxi = cand;
            ans1 = ans;
            as1 = as;
        }
        printde(cand);
        shuffle(is2.begin(), is2.end(), mt);
    }
    as = as1;
    ans = ans1;

    score = score0 - calc();
    printde(score);
    for(auto& e : ans){
        cout << e << '\n';
    }
}
0