Cod sursa(job #2012356)

Utilizator lflorin29Florin Laiu lflorin29 Data 18 august 2017 16:28:30
Problema Ghiozdan Scor 0
Compilator cpp Status done
Runda Lista lui wefgef Marime 1.92 kb
#include <bits/stdc++.h>

using namespace std;

const int G = 75000, X = 200;

int n, g;
int ap[X + 2];
int dp[2][G], ant[2][G];
deque<pair<int, int> >dq;

void initLine(bool l, int need) {
    for(int i = 0; i <= need; ++i) {
        if(i > 0) {
            dp[l][i] = n + 1;
        } else dp[l][i] = 0;
        ant[l][i] = 0;
    }
}
void solve(int st, int dr, int need) {
    if(st == dr) {
        while(ap[st] && need - st >= 0)
        {
            cout << st<<'\n'; ap[st]--;
        }
        return;
    }
    int mid = (st + dr) >> 1;
    bool l = 0;
    for(int i = 0; i < 2; ++i) initLine(i, need);
    for(int i = st; i <= dr; ++i) {
        l ^= 1;
        initLine(l, need);
        for(int r = 0; r < i; ++r) {
            dq.clear();
            for(int u = 0; u * i + r <= need; ++u) {
                int val = u * i + r;
                while(!dq.empty() && dp[l ^ 1][val] - u <= dq.back().first) {
                    dq.pop_back();
                }
                dq.push_back(make_pair(dp[l ^ 1][val] - u, val));
                while(!dq.empty() && dq.front().second <= val - (ap[i] + 1) * i) dq.pop_front();
                assert(dq.size());
                dp[l][val] = dq.front().first + u;
                if(i <= mid) {
                    ant[l][val] = val;
                } else ant[l][val] = ant[l ^ 1][dq.front().second];
            }
        }
    }
    int w = need;
    if(st == 1 && dr == 200) {
        int weight = need;
        while(weight > 0 && dp[l][weight] == n + 1)--weight;
        cout << weight << ' ' << dp[l][weight] << '\n';
        w = weight;
    }
    solve(st, mid, ant[l][w]);
    solve(mid + 1, dr, need - ant[l][w]);
}
int main() {
    ifstream cin("ghiozdan.in");
    ofstream cout("ghiozdan.out");

    cin >> n >> g;
    for(int i = 1; i <= n; ++i) {
        int x;
        cin >> x;
        ++ap[x];
    }
    solve(1, X, g);
}