답안 #993658

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
993658 2024-06-06T09:34:58 Z LOLOLO Krov (COCI17_krov) C++17
140 / 140
1068 ms 19280 KB
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
 
#define           f     first
#define           s     second
#define           pb    push_back
#define           ep    emplace
#define           eb    emplace_back
#define           lb    lower_bound
#define           ub    upper_bound
#define       all(x)    x.begin(), x.end()
#define      rall(x)    x.rbegin(), x.rend()
#define   uniquev(v)    sort(all(v)), (v).resize(unique(all(v)) - (v).begin())
#define     mem(f,x)    memset(f , x , sizeof(f))
#define        sz(x)    (ll)(x).size()
#define  __lcm(a, b)    (1ll * ((a) / __gcd((a), (b))) * (b))
#define          mxx    *max_element
#define          mnn    *min_element
#define    cntbit(x)    __builtin_popcountll(x)
#define       len(x)    (int)(x.length())

const int N = 1e5 + 100;

ll h[N], x[N], y[N];

struct fen{
    vector <ll> f;
    int n;
    void ass(int N) {
        n = N;
        f.assign(n + 1, 0);
    }

    void upd(int i, int x) {
        for (; i <= n; i += i & (-i))
            f[i] += x;
    }

    ll get(int i) {
        ll s = 0;
        for (; i; i -= i & (-i))
            s += f[i];

        return s;
    }

    ll range(int l, int r) {
        return get(r) - get(l - 1);
    }
} suml, sumr, cntl, cntr;

map <ll, ll> m1, m2;
int n;

ll get(int p, ll v) {
    ll x = v + (n - p), y = v + p; 
    auto L = *m2.lower_bound(x);
    auto R = *m1.lower_bound(y);

    ll ans = suml.range(L.s, n + 1) - x * cntl.range(L.s, n + 1);
    ans += x * cntl.get(L.s - 1) - suml.get(L.s - 1);

    ans += sumr.range(R.s, n + 1) - y * cntr.range(R.s, n + 1);
    ans += y * cntr.get(R.s - 1) - sumr.get(R.s - 1);    
    return ans;
}

ll cal(int p) {
    ll l = max(p, n - p + 1), r = 1e9 + 1, ans = 1e18;
    while (l <= r) {
        ll m = (l + r) / 2;
        ll x = get(p, m) + abs(h[p] - m), y = get(p, m + 1) + abs(h[p] - (m + 1));
        if (y <= x) {
            l = m + 1;
        } else {
            r = m - 1;
        }

        ans = min({ans, x, y});
    }

    return ans;
}

ll solve() {
    cin >> n;

    for (int i = 1; i <= n; i++) {
        cin >> h[i];
        x[i] = h[i] + i;
        y[i] = h[i] + (n - i);
        m1[x[i]];
        m2[y[i]];
    }

    m1[1e18];
    m2[1e18];

    int timer = 1;
    for (auto &x : m1)
        x.s = timer++;

    timer = 1;
    for (auto &x : m2)
        x.s = timer++;

    suml.ass(n + 1);
    sumr.ass(n + 1);
    cntl.ass(n + 1); 
    cntr.ass(n + 1);

    for (int i = 1; i <= n; i++) {
        sumr.upd(m1[x[i]], x[i]);
        cntr.upd(m1[x[i]], 1);
    }

    ll ans = 1e18;
    for (int i = 1; i <= n; i++) {
        sumr.upd(m1[x[i]], -x[i]);
        cntr.upd(m1[x[i]], -1);
        ans = min(ans, cal(i));
        suml.upd(m2[y[i]], y[i]);
        cntl.upd(m2[y[i]], 1);
    }

    return ans;
}

int main() {
    ios_base::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);

    int t = 1;
    //cin >> t;

    while (t--) {
        cout << solve() << '\n';
    }

    return 0;
}  
# 결과 실행 시간 메모리 Grader output
1 Correct 5 ms 604 KB Output is correct
2 Correct 6 ms 604 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 6 ms 604 KB Output is correct
2 Correct 5 ms 604 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 10 ms 600 KB Output is correct
2 Correct 8 ms 600 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 9 ms 860 KB Output is correct
2 Correct 12 ms 600 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 14 ms 600 KB Output is correct
2 Correct 15 ms 860 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 25 ms 1296 KB Output is correct
2 Correct 20 ms 856 KB Output is correct
3 Correct 19 ms 860 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 201 ms 4696 KB Output is correct
2 Correct 187 ms 3416 KB Output is correct
3 Correct 195 ms 4700 KB Output is correct
4 Correct 268 ms 5724 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 314 ms 7032 KB Output is correct
2 Correct 457 ms 8016 KB Output is correct
3 Correct 269 ms 7760 KB Output is correct
4 Correct 249 ms 7768 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 639 ms 8864 KB Output is correct
2 Correct 592 ms 14308 KB Output is correct
3 Correct 343 ms 6492 KB Output is correct
4 Correct 736 ms 13136 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 910 ms 19280 KB Output is correct
2 Correct 973 ms 19024 KB Output is correct
3 Correct 658 ms 13136 KB Output is correct
4 Correct 1068 ms 16944 KB Output is correct
5 Correct 159 ms 5208 KB Output is correct