Submission #131758

#TimeUsernameProblemLanguageResultExecution timeMemory
131758PeppaPigHoliday (IOI14_holiday)C++14
0 / 100
125 ms65540 KiB
#include "holiday.h"
#include <bits/stdc++.h>

#define long long long

using namespace std;

const int N = 1e5+5;

struct node {
    long sum, cnt;
    node *l, *r;
    node(long sum, long cnt, node *l, node *r) : sum(sum), cnt(cnt), l(l), r(r) { }
};

node* newleaf(long sum, long cnt) {
    return new node(sum, cnt, nullptr, nullptr);
}

node* newpar(node *l, node *r) {
    return new node(l->sum + r->sum, l->cnt + r->cnt, l, r);
}

int n, d, start, a[N];
long ans = -1;

node* build(int l = 1, int r = n) {
    if(l == r) return newleaf(0, 0);
    int mid = (l + r) >> 1;
    return newpar(build(l, mid), build(mid+1, r));
}

node* update(int x, long k, node *p, int l = 1, int r = n) {
    if(l == r) return newleaf(k, 1);
    int mid = (l + r) >> 1;
    if(x <= mid) return newpar(update(x, k, p->l, l, mid), p->r);
    else return newpar(p->l, update(x, k, p->r, mid+1, r));
}

long query(int k, node *pl, node *pr, int l = 1, int r = n) {
    if(!k) return 0;
    if(l == r) return pr->sum - pl->sum;
    long sum_r = pr->r->sum - pl->r->sum, cnt_r = pr->r->cnt - pl->r->cnt;
    int mid = (l + r) >> 1;
    if(cnt_r >= k) return query(k, pl->r, pr->r, mid+1, r);
    else return sum_r + query(k - cnt_r, pl->l, pr->l, l, mid);
}

node* t[N];
vector<int> coord;

void solve(int l, int r, int optl, int optr) {
    if(l > r) return;
    int mid = (l + r) >> 1;
    long ret = -1, idx = optl;
    for(int i = max(optl, mid); i <= min(mid + d - 1, optr); i++) {
        int cost = i - mid - min(abs(start - mid), abs(start - i));
        if(d - cost - 2 < 0) continue;
        long q = query(d - cost - 2, t[mid], t[i-1]) + a[mid] + a[i];
        if(q > ret) ret = q, idx = i;
    }
    ans = max(ans, ret);
    solve(l, mid - 1, optl, idx);
    solve(mid+1, r, idx, optr);
}

long findMaxAttraction(int _n, int _start, int _d, int _a[]) {
    n = _n, start = _start + 1, d = _d;
    for(int i = 1; i <= n; i++) a[i] = _a[i-1], coord.emplace_back(a[i-1]);

    sort(coord.begin(), coord.end());
    map<int, int> M;
    t[0] = build();
    for(int i = 1; i <= n; i++) {
        int idx = lower_bound(coord.begin(), coord.end(), a[i]) - coord.begin() + 1 + M[a[i]]++;
        t[i] = update(idx, a[i], t[i-1]);
    }
    solve(max(1, start - d), min(n, start + d), 1, n);

    return ans;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...