제출 #1369714

#제출 시각아이디문제언어결과실행 시간메모리
1369714vlad7654운세 보기 2 (JOI14_fortune_telling2)C++20
100 / 100
318 ms28072 KiB
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
vector<pair<int, int>> v;
vector<int> queries, normalizare;
vector<vector<int>> queries_at;
const int NMAX = 600005;
struct ST {
    int tree[4 * NMAX + 5];
    void update(int poz, int val, int l = 0, int r = NMAX, int node = 1) {
        if (l == r) {
            tree[node] = val;
            return;
        }
        int mid = (l + r) / 2;
        if (poz <= mid) update(poz, val, l, mid, node * 2);
        else update(poz, val, mid + 1, r, node * 2 + 1);
        tree[node] = max(tree[node * 2], tree[node * 2 + 1]);
    }
    int query(int left, int right, int l = 0, int r = NMAX, int node = 1) {
        if (left > r or l > right or left > right) return 0;
        if (l >= left and r <= right) return tree[node];
        int mid = (l + r) / 2;
        return max(query(left, right, l, mid, 2 * node), query(left, right, mid + 1, r, 2 * node + 1));
    }
};

struct ST2 {
    int tree[4 * NMAX + 5];
    void update(int poz, int val, int l = 0, int r = NMAX, int node = 1) {
        if (l == r) {
            tree[node] += val;
            return;
        }
        int mid = (l + r) / 2;
        if (poz <= mid) update(poz, val, l, mid, node * 2);
        else update(poz, val, mid + 1, r, node * 2 + 1);
        tree[node] = tree[node * 2] + tree[node * 2 + 1];
    }
    int query(int left, int right, int l = 0, int r = NMAX, int node = 1) {
        if (left > r or l > right or left > right) return 0;
        if (l >= left and r <= right) return tree[node];
        int mid = (l + r) / 2;
        return query(left, right, l, mid, 2 * node) + query(left, right, mid + 1, r, 2 * node + 1);
    }
};
ST tree_rmq;
ST2 tree_sum;
int main() {
    cin.tie(0)->sync_with_stdio(0);
    int n, k;
    cin >> n >> k;
    v.resize(n + 1);
    queries.resize(k + 1);
    queries_at.resize(k + 1);
    for (int i = 1; i <= n; i++) {
        cin >> v[i].first >> v[i].second;
        normalizare.push_back(v[i].first);
        normalizare.push_back(v[i].second);
    }
    for (int i = 1; i <= k; i++) {
        cin >> queries[i];
        normalizare.push_back(queries[i]);
    }
    sort(normalizare.begin(), normalizare.end());
    normalizare.erase(unique(normalizare.begin(), normalizare.end()), normalizare.end());
    int M = normalizare.size() - 1;
    for (int i = 1; i <= k; i++) {
        int poz = lower_bound(normalizare.begin(), normalizare.end(), queries[i]) - normalizare.begin();
        tree_rmq.update(poz, i, 0, M);
    }
    for (int i = 1; i <= n; i++) {
        int L_val = min(v[i].first, v[i].second);
        int R_val = max(v[i].first, v[i].second);
        int left = lower_bound(normalizare.begin(), normalizare.end(), L_val) - normalizare.begin();
        int right = lower_bound(normalizare.begin(), normalizare.end(), R_val) - normalizare.begin() - 1;
        int last_t = 0;
        if (left <= right) last_t = tree_rmq.query(left, right, 0, M);
        queries_at[last_t].push_back(i);
    }
    ll total_cnt = 0;
    for (int i = k; i >= 0; i--) {
        for (auto it : queries_at[i]) {
            int mx = max(v[it].first, v[it].second);
            int mn = min(v[it].first, v[it].second);
            int poz = lower_bound(normalizare.begin(), normalizare.end(), mx) - normalizare.begin();
            int flips = tree_sum.query(poz, M, 0, M);
            int current_face;
            if (i == 0) current_face = v[it].first;
            else current_face = mx;
            if (flips % 2 == 1) {
                if (current_face == v[it].first) {
                    total_cnt += v[it].second;
                } else {
                    total_cnt += v[it].first;
                }
            } else {
                total_cnt += current_face;
            }
        }
        if (i > 0) {
            int op_poz = lower_bound(normalizare.begin(), normalizare.end(), queries[i]) - normalizare.begin();
            tree_sum.update(op_poz, 1, 0, M);
        }
    }
    cout << total_cnt;
}
#결과 실행 시간메모리채점기 출력
결과를 불러오는 중입니다…
#결과 실행 시간메모리채점기 출력
결과를 불러오는 중입니다…
#결과 실행 시간메모리채점기 출력
결과를 불러오는 중입니다…