답안 #1110999

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
1110999 2024-11-11T09:26:26 Z thieunguyenhuy 나일강 (IOI24_nile) C++17
100 / 100
88 ms 15568 KB
#include <bits/stdc++.h>
using namespace std;

#define popcount(n) (__builtin_popcountll((n)))
#define clz(n) (__builtin_clzll((n)))
#define ctz(n) (__builtin_ctzll((n)))
#define lg(n) (63 - __builtin_clzll((n)))
#define BIT(n, i) (((n) >> (i)) & 1ll)
#define MASK(i) (1ll << (i))
#define FLIP(n, i) ((n) ^ (1ll << (i)))
#define ON(n, i) ((n) | MASK(i))
#define OFF(n, i) ((n) & ~MASK(i))

#define Int __int128
#define fi first
#define se second

typedef long long ll;
typedef unsigned long long ull;
typedef long double ld;
typedef pair<int, int> pii;
typedef pair<long long, long long> pll;
typedef pair<long long, int> pli;
typedef pair<int, long long> pil;
typedef vector<pair<int, int>> vii;
typedef vector<pair<long long, long long>> vll;
typedef vector<pair<long long, int>> vli;
typedef vector<pair<int, long long>> vil;

template <class T1, class T2>
bool maximize(T1 &x, T2 y) {
    if (x < y) {
        x = y;
        return true;
    }
    return false;
}
template <class T1, class T2>
bool minimize(T1 &x, T2 y) {
    if (x > y) {
        x = y;
        return true;
    }
    return false;
}

template <class T>
void remove_duplicate(vector<T> &ve) {
    sort (ve.begin(), ve.end());
    ve.resize(unique(ve.begin(), ve.end()) - ve.begin());
}

mt19937 rng(chrono::high_resolution_clock::now().time_since_epoch().count());
template <class T> T random(T l, T r) {
    return uniform_int_distribution<T>(l, r)(rng);
}
template <class T> T random(T r) {
    return rng() % r;
}

const int N = 1e5 + 5;
const int MOD = 1e9 + 7;
const int inf = 1e9;
const ll INF = 1e18;

int n, q, D;
ll ans;
ll pref[N];
vii edges, que;

struct Artifact {
    int w, one, two;

    Artifact(int _w = 0, int _one = 0, int _two = 0) {
        w = _w, one = _one, two = _two;
    }

    bool operator< (const Artifact &other) {
        return w < other.w;
    }
} a[N];

struct DSU {
    struct Component {
        int lab, L, R;
        int best_odd, best_even;
        int odd, even;

        Component() {
            lab = -1, L = R = 0;
            best_odd = best_even = odd = even = -1;
        }

        void show() {
            cerr << "mk " << lab << ' ' << L << ' ' << R << ' ' << best_odd << ' ' << best_even << ' ' << odd << ' ' << even << ' ' << eval() << '\n';
        }

        ll eval() {
            assert(-lab == R - L + 1);
            ll ret = pref[R] - pref[L - 1];
            // if (L == 2 && R == 5) {
            //     cerr << "ret = " << ret << '\n';
            // }
            if ((-lab) & 1) {
                // cerr << L << ' ' << R << '\n';
                int mi = inf;
                if (best_odd != -1) minimize(mi, a[best_odd].one - a[best_odd].two);
                if (even != -1) minimize(mi, a[even].one - a[even].two);
                // for (int i = L; i <= R; i += 2) minimize(real_mi, a[i].one - a[i].two);
                // for (int i = L + 1; i < R; i += 2) if (a[i + 1].w - a[i - 1].w <= D) {
                //     minimize(real_mi, a[i].one - a[i].two);
                // }
                assert(mi < inf);
                ret += mi;
                // real_ret += real_mi;
            }
            // assert(real_ret == ret);
            return ret;
        }
    };

    vector<Component> comp;

    void resize(int n) {
        comp.assign(n + 1, Component());
        for (int i = 1; i <= n; ++i) {
            // comp[i].lab = -1;
            comp[i].L = comp[i].R = i;
            comp[i].best_odd = i;
            ans += a[i].one;
        }
    }

    int find_set(int p) {
        return comp[p].lab < 0 ? p : comp[p].lab = find_set(comp[p].lab);
    }

    bool compare(int p, int q) {
        if (q == -1) return true;
        if (p == -1) return false;
        return a[p].one - a[p].two < a[q].one - a[q].two;
    }

    void update(int &x, int y) {
        if (compare(y, x)) x = y;
    }

    Component merge(Component A, Component B) {
        // cerr << A.L << ' ' << A.R << ' ' << B.L << ' ' << B.R << '\n';
        if (A.L > B.R) swap(A, B);
        // if (make_pair(A.L, A.R) == make_pair(2, 2)) {
        //     A.show(), B.show();
        // }
        if ((-A.lab) & 1) {
            update(A.best_odd, B.best_even);
            update(A.best_even, B.best_odd);
            update(A.odd, B.even);
            update(A.even, B.odd);
        }
        else {
            update(A.best_odd, B.best_odd);
            update(A.best_even, B.best_even);
            update(A.odd, B.odd);
            update(A.even, B.even);
        }
        A.R = B.R, A.lab += B.lab;
        return A;
    }

    bool join(int u, int v) {
        u = find_set(u), v = find_set(v);
        if (u != v) {
            if (comp[u].lab > comp[v].lab) swap(u, v);
            ans -= comp[u].eval() + comp[v].eval();
            comp[u] = merge(comp[u], comp[v]);
            comp[v].lab = u;
            // if (comp[u].L == 2 && comp[u].R == 4) {
            //     comp[u].show(), comp[v].show();
            // }
            ans += comp[u].eval();
            return true;
        }
        return false;
    }
} dsu;

vector<long long> calculate_costs(vector<int> W, vector<int> A, vector<int> B, vector<int> E) {
    n = W.size(), q = E.size();

    for (int i = 1; i <= n; ++i) {
        a[i] = Artifact(W[i - 1], A[i - 1], B[i - 1]);
    }

    sort (a + 1, a + 1 + n);
    for (int i = 1; i <= n; ++i) {
        pref[i] = pref[i - 1] + a[i].two;
        if (i < n) edges.emplace_back(a[i + 1].w - a[i].w, -i);
        if (i + 1 < n) edges.emplace_back(a[i + 2].w - a[i].w, i + 1);
    }

    sort (edges.begin(), edges.end());

    for (int i = 0; i < q; ++i) {
        int d = E[i];
        que.emplace_back(d, i);
    }

    sort (que.begin(), que.end());

    int p = -1; dsu.resize(n); vector<ll> res(q);
    for (auto &[d, id] : que) {
        D = d;
        while (p + 1 < edges.size() && edges[p + 1].fi <= d) {
            int i = edges[++p].se;
            if (i < 0) dsu.join(-i, -i + 1);
            else {
                // i = -i;
                int s = dsu.find_set(i);
                // assert(dsu.find_set(i - 1) == s && s == dsu.find_set(i + 1));
                if (i % 2 == dsu.comp[s].L % 2) {
                    dsu.update(dsu.comp[s].odd, i);
                }
                else {
                    ans -= dsu.comp[s].eval();
                    dsu.update(dsu.comp[s].even, i);
                    ans += dsu.comp[s].eval();
                }
            }
        }
        // if (id == 1) {
        //     for (int i = 1; i <= n; ++i) if (dsu.find_set(i) == i) {
        //         dsu.comp[i].show();
        //     }   
        // }
        res[id] = ans;
    }

    return res;
}

#ifdef hwe
signed main() {
    ios_base::sync_with_stdio(false); cin.tie(NULL); cout.tie(NULL);

    #ifdef hwe
        freopen("input.inp", "r", stdin);
        freopen("output.out", "w", stdout);
    #else
        #define taskname ""
        if (fopen(taskname".inp", "r")) {
            freopen(taskname".inp", "r", stdin);
            freopen(taskname".out", "w", stdout);
        }
    #endif

    cerr << '\n'; return 0;
}
#endif

Compilation message

nile.cpp: In function 'std::vector<long long int> calculate_costs(std::vector<int>, std::vector<int>, std::vector<int>, std::vector<int>)':
nile.cpp:213:22: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<std::pair<int, int> >::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  213 |         while (p + 1 < edges.size() && edges[p + 1].fi <= d) {
      |                ~~~~~~^~~~~~~~~~~~~~
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 1616 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 1616 KB Output is correct
2 Correct 2 ms 1616 KB Output is correct
3 Correct 2 ms 1616 KB Output is correct
4 Correct 2 ms 1696 KB Output is correct
5 Correct 3 ms 1720 KB Output is correct
6 Correct 2 ms 1616 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 36 ms 11988 KB Output is correct
2 Correct 37 ms 12104 KB Output is correct
3 Correct 37 ms 12092 KB Output is correct
4 Correct 38 ms 11960 KB Output is correct
5 Correct 38 ms 11976 KB Output is correct
6 Correct 38 ms 11988 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 38 ms 10700 KB Output is correct
2 Correct 38 ms 10936 KB Output is correct
3 Correct 55 ms 10952 KB Output is correct
4 Correct 49 ms 10936 KB Output is correct
5 Correct 45 ms 10928 KB Output is correct
6 Correct 51 ms 10928 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 1616 KB Output is correct
2 Correct 2 ms 1616 KB Output is correct
3 Correct 2 ms 1616 KB Output is correct
4 Correct 2 ms 1696 KB Output is correct
5 Correct 3 ms 1720 KB Output is correct
6 Correct 2 ms 1616 KB Output is correct
7 Correct 2 ms 1616 KB Output is correct
8 Correct 3 ms 1616 KB Output is correct
9 Correct 3 ms 1616 KB Output is correct
10 Correct 3 ms 1788 KB Output is correct
11 Correct 2 ms 1616 KB Output is correct
12 Correct 3 ms 1792 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 1616 KB Output is correct
2 Correct 2 ms 1616 KB Output is correct
3 Correct 2 ms 1616 KB Output is correct
4 Correct 2 ms 1696 KB Output is correct
5 Correct 3 ms 1720 KB Output is correct
6 Correct 2 ms 1616 KB Output is correct
7 Correct 36 ms 11988 KB Output is correct
8 Correct 37 ms 12104 KB Output is correct
9 Correct 37 ms 12092 KB Output is correct
10 Correct 38 ms 11960 KB Output is correct
11 Correct 38 ms 11976 KB Output is correct
12 Correct 38 ms 11988 KB Output is correct
13 Correct 38 ms 10700 KB Output is correct
14 Correct 38 ms 10936 KB Output is correct
15 Correct 55 ms 10952 KB Output is correct
16 Correct 49 ms 10936 KB Output is correct
17 Correct 45 ms 10928 KB Output is correct
18 Correct 51 ms 10928 KB Output is correct
19 Correct 2 ms 1616 KB Output is correct
20 Correct 3 ms 1616 KB Output is correct
21 Correct 3 ms 1616 KB Output is correct
22 Correct 3 ms 1788 KB Output is correct
23 Correct 2 ms 1616 KB Output is correct
24 Correct 3 ms 1792 KB Output is correct
25 Correct 47 ms 12232 KB Output is correct
26 Correct 46 ms 12472 KB Output is correct
27 Correct 54 ms 12448 KB Output is correct
28 Correct 55 ms 12472 KB Output is correct
29 Correct 53 ms 12360 KB Output is correct
30 Correct 58 ms 12472 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 38 ms 10700 KB Output is correct
2 Correct 38 ms 10936 KB Output is correct
3 Correct 55 ms 10952 KB Output is correct
4 Correct 49 ms 10936 KB Output is correct
5 Correct 45 ms 10928 KB Output is correct
6 Correct 51 ms 10928 KB Output is correct
7 Correct 63 ms 13760 KB Output is correct
8 Correct 59 ms 14008 KB Output is correct
9 Correct 68 ms 13956 KB Output is correct
10 Correct 67 ms 14008 KB Output is correct
11 Correct 70 ms 14008 KB Output is correct
12 Correct 69 ms 13956 KB Output is correct
13 Correct 70 ms 14264 KB Output is correct
14 Correct 66 ms 13752 KB Output is correct
15 Correct 72 ms 13944 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 1616 KB Output is correct
2 Correct 2 ms 1616 KB Output is correct
3 Correct 2 ms 1616 KB Output is correct
4 Correct 2 ms 1616 KB Output is correct
5 Correct 2 ms 1696 KB Output is correct
6 Correct 3 ms 1720 KB Output is correct
7 Correct 2 ms 1616 KB Output is correct
8 Correct 36 ms 11988 KB Output is correct
9 Correct 37 ms 12104 KB Output is correct
10 Correct 37 ms 12092 KB Output is correct
11 Correct 38 ms 11960 KB Output is correct
12 Correct 38 ms 11976 KB Output is correct
13 Correct 38 ms 11988 KB Output is correct
14 Correct 38 ms 10700 KB Output is correct
15 Correct 38 ms 10936 KB Output is correct
16 Correct 55 ms 10952 KB Output is correct
17 Correct 49 ms 10936 KB Output is correct
18 Correct 45 ms 10928 KB Output is correct
19 Correct 51 ms 10928 KB Output is correct
20 Correct 2 ms 1616 KB Output is correct
21 Correct 3 ms 1616 KB Output is correct
22 Correct 3 ms 1616 KB Output is correct
23 Correct 3 ms 1788 KB Output is correct
24 Correct 2 ms 1616 KB Output is correct
25 Correct 3 ms 1792 KB Output is correct
26 Correct 47 ms 12232 KB Output is correct
27 Correct 46 ms 12472 KB Output is correct
28 Correct 54 ms 12448 KB Output is correct
29 Correct 55 ms 12472 KB Output is correct
30 Correct 53 ms 12360 KB Output is correct
31 Correct 58 ms 12472 KB Output is correct
32 Correct 63 ms 13760 KB Output is correct
33 Correct 59 ms 14008 KB Output is correct
34 Correct 68 ms 13956 KB Output is correct
35 Correct 67 ms 14008 KB Output is correct
36 Correct 70 ms 14008 KB Output is correct
37 Correct 69 ms 13956 KB Output is correct
38 Correct 70 ms 14264 KB Output is correct
39 Correct 66 ms 13752 KB Output is correct
40 Correct 72 ms 13944 KB Output is correct
41 Correct 67 ms 15188 KB Output is correct
42 Correct 66 ms 15464 KB Output is correct
43 Correct 84 ms 15516 KB Output is correct
44 Correct 76 ms 15544 KB Output is correct
45 Correct 75 ms 15568 KB Output is correct
46 Correct 76 ms 15544 KB Output is correct
47 Correct 80 ms 15544 KB Output is correct
48 Correct 77 ms 15300 KB Output is correct
49 Correct 88 ms 15544 KB Output is correct