Codeforces 1016F Road Projects

Road Projects

根据基环分类讨论讨论。。

#include<bits/stdc++.h>
#define LL long long
#define LD long double
#define ull unsigned long long
#define fi first
#define se second
#define mk make_pair
#define PLL pair<LL, LL>
#define PLI pair<LL, int>
#define PII pair<int, int>
#define SZ(x) ((int)x.size())
#define ALL(x) (x).begin(), (x).end()
#define fio ios::sync_with_stdio(false); cin.tie(0);

using namespace std;

const int N = 3e5 + 7;
const int inf = 0x3f3f3f3f;
const LL INF = 0x3f3f3f3f3f3f3f3f;
const int mod = 1e9 + 7;
const double eps = 1e-8;
const double PI = acos(-1);

template<class T, class S> inline void add(T& a, S b) {a += b; if(a >= mod) a -= mod;}
template<class T, class S> inline void sub(T& a, S b) {a -= b; if(a < 0) a += mod;}
template<class T, class S> inline bool chkmax(T& a, S b) {return a < b ? a = b, true : false;}
template<class T, class S> inline bool chkmin(T& a, S b) {return a > b ? a = b, true : false;}

int n, m, pa[N];
int road[N], cntr;
LL depth[N];
LL dis[N], mx[N];
int sum[N];
bool ban[N];

LL v1[N], v2[N];
LL sufmx[N];

vector<PII> G[N];

void dfs(int u, int fa) {
    pa[u] = fa;
    for(auto& e : G[u]) {
        if(e.se == fa) continue;
        depth[e.se] = depth[u] + e.fi;
        dfs(e.se, u);
    }
}

LL dfs2(int u, int fa, int& sum) {
    LL mx = dis[u];
    sum++;
    for(auto& e : G[u]) {
        if(e.se == fa || ban[e.se]) continue;
        dis[e.se] = dis[u] + e.fi;
        chkmax(mx, dfs2(e.se, u, sum));
    }
    return mx;
}

int main() {
    scanf("%d%d", &n, &m);
    for(int i = 1; i < n; i++) {
        int u, v, w;
        scanf("%d%d%d", &u, &v, &w);
        G[u].push_back(mk(w, v));
        G[v].push_back(mk(w, u));
    }
    bool can = false;
    dfs(1, 0);
    int now = n;
    while(now) {
        road[++cntr] = now;
        now = pa[now];
    }
    reverse(road + 1, road + 1 + cntr);
    for(int i = 1; i <= n; i++) ban[road[i]] = true;
    for(int i = 1; i <= cntr; i++) {
        mx[i] = dfs2(road[i], 0, sum[i]);
        if(sum[i] >= 3) can = true;
    }
    LL tmp = depth[n];
    LL ret = INF;
    if(!can) {
        ret = 0;
        chkmax(ret, dis[1] + dis[n]);
        for(int i = 1; i <= cntr; i++) {
            int u = road[i];
            v1[i] = depth[u] + mx[i];
            v2[i] = mx[i] - depth[u];
        }
        sufmx[cntr] = v2[cntr];
        for(int i = cntr - 1; i >= 1; i--)
            sufmx[i] = max(v2[i], sufmx[i + 1]);
        for(int i = 1; i < cntr; i++) {
            if(sum[i] == 1 && sum[i + 1] == 1 && i + 2 <= cntr)
                chkmax(ret, v1[i] + sufmx[i + 2] + depth[n]);
            else if(sum[i] > 1 || sum[i + 1] > 1)
                chkmax(ret, v1[i] + sufmx[i + 1] + depth[n]);
        }
        if(cntr >= 3) {
            if(sum[1] >= 2) chkmax(ret, tmp - depth[road[2]] + mx[1]);
            if(sum[cntr] >= 2) chkmax(ret, tmp - (depth[n] - depth[road[cntr - 1]]) + mx[cntr]);
        }
    }
    while(m--) {
        int x; scanf("%d", &x);
        printf("%lld
", min(tmp, ret + x));
    }
    return 0;
}

/*
*/
原文地址:https://www.cnblogs.com/CJLHY/p/10819492.html