Submission #1223908

#TimeUsernameProblemLanguageResultExecution timeMemory
1223908banganRarest Insects (IOI22_insects)C++20
57.25 / 100
45 ms452 KiB
#include "insects.h"
#include <bits/stdc++.h>
using namespace std;

#define pb push_back

mt19937_64 rng(chrono::steady_clock::now().time_since_epoch().count());

int n;
int unq;
vector<int> in;
vector<bool> is_in;
int last = 1;

bool ok(int k) {
    if (k < last) {
        while (!in.empty()) {
            move_outside(in.back());
            is_in[in.back()] = false;
            in.pop_back();
        }
    }
    last = k;

    vector<int> all;
    for (int i=0; i<n; i++) if (!is_in[i]) all.pb(i);
    shuffle(all.begin(), all.end(), rng);
    for (int i : all) {
        move_inside(i);
        if (press_button() > k) move_outside(i);
        else in.pb(i), is_in[i] = true;
        if (unq * k == in.size()) return true;
    }
    return false;
}

int min_cardinality(int N) {
    is_in.resize(N);
    for (int i = 0; i < N; i++) {
        move_inside(i);
        if (press_button() == 2) move_outside(i);
        else in.pb(i), is_in[i] = true;
    }
    unq = in.size();

    if (unq <= 16) {
        while (!in.empty()) {
            move_outside(in.back());
            is_in[in.back()] = false;
            in.pop_back();
        }

        vector<int> all;
        for (int i=0; i<N; i++) all.pb(i);

        unq--;
        int ans = N;
        while (unq--) {
            vector<int> rem;
            int cur = 0;
            while (!all.empty()) {
                int i = all.back();
                all.pop_back();
                move_inside(i);
                int res = press_button();
                if (res == cur) {
                    move_outside(i);
                    rem.pb(i);
                }
                else {
                    in.pb(i);
                }
                cur = res;
            }
            ans = min(ans, cur);
            if (ans == 1) return 1;
            all = rem;
            while (!in.empty()) {
                move_outside(in.back());
                in.pop_back();
            }
        }
        return min((int) all.size(), ans);
    }

    n = N;
    int l = 1, r = n / unq;
    while (l != r) {
        int mid = (l+r+1) / 2;
        ok(mid) ? l = mid : r = mid - 1;
    }
    return l;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...