제출 #1330912

#제출 시각아이디문제언어결과실행 시간메모리
1330912chikien2009별자리 3 (JOI20_constellation3)C++20
100 / 100
279 ms94380 KiB
#include <bits/stdc++.h>

using namespace std;

void setup()
{
// #ifndef ONLINE_JUDGE
//     freopen("test.inp", "r", stdin);
//     freopen("test.out", "w", stdout);
// #endif
    ios_base::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);
}

int n, m, b, c, d, root;
int a[200000], sp[20][200000];
long long sum;
vector<int> g[200000];
vector<pair<int, int>> stars[200000];
pair<long long, set<pair<int, long long>>> res;

inline int Get(int l, int r)
{
    int k = __lg(r - l + 1);
    return (a[sp[k][l]] > a[sp[k][r - (1 << k) + 1]] ? sp[k][l] : sp[k][r - (1 << k) + 1]);
}

inline void Build(int l, int r, int par = -1)
{
    int mid = Get(l, r);
    if (par != -1)
    {
        g[par].push_back(mid);
    }
    else
    {
        root = mid;
    }
    if (l < mid)
    {
        Build(l, mid - 1, mid);
    }
    if (mid < r)
    {
        Build(mid + 1, r, mid);
    }
}

inline void Add(set<pair<int, long long>> & s, pair<int, long long> p)
{
    set<pair<int, long long>>::iterator it;
    s.insert(p);
    it = s.lower_bound(p);
    if (it != s.begin() && (*prev(it)).second >= p.second)
    {
        s.erase(it);
        return;
    }
    while ((it = s.lower_bound(p)) != prev(s.end()) &&
           (*next(it)).second <= p.second)
    {
        s.erase(next(it));
    }
}

inline pair<long long, set<pair<int, long long>>> DFS(int node)
{
    pair<long long, set<pair<int, long long>>> cur, temp;
    set<pair<int, long long>>::iterator it;
    long long base;
    for (auto &i : stars[node])
    {
        Add(cur.second, i);
    }
    for (auto &i : g[node])
    {
        temp = DFS(i);
        if (temp.second.size() > cur.second.size())
        {
            swap(temp, cur);
        }

        it = cur.second.upper_bound({a[node], 1e18});
        base = (it == cur.second.begin() ? 0LL : (*prev(it)).second + cur.first);

        it = temp.second.upper_bound({a[node], 1e18});
        if (it != temp.second.begin())
        {
            cur.first += (*prev(it)).second + temp.first;
        }

        for (auto &j : temp.second)
        {
            Add(cur.second, {j.first, j.second + temp.first + base - cur.first});
        }
    }
    return cur;
}

int main()
{
    setup();

    cin >> n;
    for (int i = 0; i < n; ++i)
    {
        cin >> a[i];
        sp[0][i] = i;
    }
    for (int i = 1; i <= __lg(n); ++i)
    {
        for (int j = 0; j < n; ++j)
        {
            sp[i][j] = (a[sp[i - 1][j]] > a[sp[i - 1][j + (1 << (i - 1))]] ? sp[i - 1][j] : sp[i - 1][j + (1 << (i - 1))]);
        }
    }
    Build(0, n - 1);
    cin >> m;
    while (m--)
    {
        cin >> b >> c >> d;
        sum += d;
        stars[b - 1].push_back({c, d});
    }
    res = DFS(root);
    sum -= res.first;
    sum -= (*prev(res.second.end())).second;
    cout << sum << "\n";
    return 0;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...