QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#422595#2070. Heavy StonesAPJifengcWA 0ms18312kbC++144.0kb2024-05-27 17:06:462024-05-27 17:06:46

Judging History

你现在查看的是最新测评结果

  • [2024-05-27 17:06:46]
  • 评测
  • 测评结果:WA
  • 用时:0ms
  • 内存:18312kb
  • [2024-05-27 17:06:46]
  • 提交

answer

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 200005;
typedef tuple<long double, int, int> Slope;
int n, a[MAXN];
pair<int, int> b[MAXN];
pair<int, int> stk[MAXN];
long long pp[MAXN], pr[MAXN];
int top;
struct Update {
    int l, r, t;
};
vector<Update> pre[MAXN], suf[MAXN];
long long ans;
Slope slope(int i, int j) {
    return { 1.0l * (pp[j] - pp[i - 1]) / (j - i + 1), i, j };
}
Slope vl[MAXN << 2];
int vc;
struct BinaryIndexTree {
    long long a[MAXN << 2];
#define lowbit(x) (x & (-x))
    void add(int d, long long v) {
        // printf("bit add %d %lld\n", d, v);
        while (d <= vc) a[d] += v, d += lowbit(d);
    }
    long long query(int d) {
        long long ret = 0;
        // printf("bit query %d ", d);
        while (d) ret += a[d], d -= lowbit(d);
        // printf("%lld\n", ret);
        return ret;
    }
} bit1, bit2;
void add(int l, int r, bool type) {
    int i = lower_bound(vl + 1, vl + 1 + vc, slope(l, r)) - vl;
    // printf("added [%d, %d], %d, id = %d\n", l, r, type, i);
    int len = r - l + 1;
    long long sum = pp[r] - pp[l - 1];
    long long qs = pr[r] - pr[l - 1];
    long long psum;
    if (type == 0) {
        psum = qs - l * sum;
    } else {
        psum = (len + l - 1) * sum - qs;
    }
    // printf("psum = %lld\n", psum);
    ans += psum;
    // printf("rb = %lld\n", (bit1.query(vc) - bit1.query(i)) * sum);
    ans += (bit1.query(vc) - bit1.query(i)) * sum;
    // printf("lb = %lld\n", bit2.query(i - 1) * len);
    ans += bit2.query(i - 1) * len;
    bit1.add(i, len);
    bit2.add(i, sum);
}
void erase(int l, int r, bool type) {
    int i = lower_bound(vl + 1, vl + 1 + vc, slope(l, r)) - vl;
    // printf("erased [%d, %d], %d, id = %d\n", l, r, type, i);
    int len = r - l + 1;
    long long sum = pp[r] - pp[l - 1];
    long long qs = pr[r] - pr[l - 1];
    if (type == 0) {
        long long psum = qs - l * sum;
        ans -= psum;
    } else {
        long long psum = (len + l - 1) * sum - qs;
        ans -= psum;
    }
    ans -= (bit1.query(vc) - bit1.query(i)) * sum;
    ans -= bit2.query(i - 1) * len;
    bit1.add(i, -len);
    bit2.add(i, -sum);
}
int main() {
    // freopen("freight.in", "r", stdin);
    // freopen("freight.out", "w", stdout);
    scanf("%d", &n);
    for (int i = 1; i <= n; i++) scanf("%d", &a[i]), b[i] = { a[i], i };
    for (int i = 1; i <= n; i++) pp[i] = pp[i - 1] + a[i];
    for (int i = 1; i <= n; i++) pr[i] = pr[i - 1] + 1ll * i * a[i];
    sort(b + 1, b + 1 + n);
    for (int i = 1; i <= n; i++) {
        while (top && slope(stk[top].first, stk[top].second) < slope(stk[top].second + 1, i)) {
            pre[i].push_back({ stk[top].first, stk[top].second, -1 });
            top--;
        }
        int l = stk[top].second + 1;
        stk[++top] = { l, i };
        pre[i].push_back({ stk[top].first, stk[top].second, 1 });
        vl[++vc] = slope(stk[top].first, stk[top].second);
    }
    top = 0;
    for (int i = n; i >= 2; i--) {
        while (top && slope(i, stk[top].first - 1) > slope(stk[top].first, stk[top].second)) {
            suf[i].push_back({ stk[top].first, stk[top].second, 1 });
            vl[++vc] = slope(stk[top].first, stk[top].second);
            top--;
        }
        int r = top ? stk[top].first - 1 : n;
        stk[++top] = { i, r };
        suf[i].push_back({ stk[top].first, stk[top].second, -1 });
        vl[++vc] = slope(stk[top].first, stk[top].second);
        reverse(suf[i].begin(), suf[i].end());
    }
    sort(vl + 1, vl + 1 + vc);
    vc = unique(vl + 1, vl + 1 + vc) - vl - 1;
    cerr << vc << endl;
    for (int i = top; i >= 1; i--) {
        int l = stk[i].first, r = stk[i].second;
        add(l, r, 1);
    }
    for (int i = 1; i <= n; i++) {
        printf("%lld ", ans + 1ll * (n - 1) * a[i]);
        for (auto [l, r, k] : suf[i + 1]) {
            if (k == 1) add(l, r, 1);
            else erase(l, r, 1);
        }
        for (auto [l, r, k] : pre[i]) {
            if (k == 1) add(l, r, 0);
            else erase(l, r, 0);
        }
    }
    printf("\n");
    return 0;
}

详细

Test #1:

score: 0
Wrong Answer
time: 0ms
memory: 18312kb

input:

5
2 1 3 5 4

output:

22 21 24 33 38 

result:

wrong answer 1st lines differ - expected: '35 35 36 43 49', found: '22 21 24 33 38 '