50分,全是TLE,大概是因为另建了虚树???
查看原帖
50分,全是TLE,大概是因为另建了虚树???
1067789
Director_Ni楼主2025/7/1 19:27

已经把能卡的都卡了(qwq)不知道是什么逻辑

#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 250005, M = 5e5 + 5, LN = 19;
// const int N = 11, M = 20, LN = 5;
struct Edge
{
    int to, next, w;
} e[M];
int head[N], hv[N], idx = 0, idv = 0;
void addedge(int u, int v, int w)
{
    e[idx].to = v;
    e[idx].next = head[u];
    e[idx].w = w;
    head[u] = idx++;
}
struct Vedge
{
    int to, next;
} ev[N];
void addev(int u, int v)
{
    ev[idv].to = v;
    ev[idv].next = hv[u];
    hv[u] = idv++;
}
int f[N][LN], mic[N];
bool cho[N];
int dfn[N], a[N];
int d[N];
int n, m, k;
int dp[N];
bool cmp(int a, int b) { return dfn[a] < dfn[b]; }
void init()
{
    memset(hv, -1, sizeof hv);
    memset(cho, 0, sizeof cho);
    memset(dp, 0, sizeof dp);
    idv = 0;
}
void dfs(int x)
{
    if (cho[x])
    {
        dp[x] = mic[x];
        return;
    }
    for (int i = hv[x]; ~i; i = ev[i].next)
    {
        int v = ev[i].to;
        dfs(v);
        dp[x] += dp[v];
    }
    dp[x] = min(dp[x], mic[x]);
}
int glca(int p, int q)
{
    if (d[p] < d[q])
        swap(p, q);
    int res = d[p] - d[q];
    for (int j = LN - 1; j >= 0; --j)
        if (res & (1 << j))
            p = f[p][j];
    if (p == q)
        return p;
    for (int j = LN - 1; j >= 0; --j)
        if (f[p][j] != f[q][j])
            p = f[p][j], q = f[q][j];
    return f[p][0];
}
void build()
{
    sort(a + 1, a + 1 + k, cmp);
    int st[N], top = 0;
    st[++top] = 1;
    for (int i = 1; i <= k; ++i)
    {
        if (a[i] == 1)
            continue;
        int lca = glca(st[top], a[i]);
        if (lca != st[top]) // 等于则不必理会
        {
            while (top > 1 && !(d[st[top - 1]] < d[lca]))
            {
                addev(st[top - 1], st[top]);
                --top;
            }
            if (lca != st[top])
            { // 等于则不必理会
                addev(lca, st[top]);
                st[top] = lca;
            }
        }
        st[++top] = a[i];
    }
    while (top > 1)
    {
        addev(st[top - 1], st[top]);
        --top;
    }
}
void gf()
{
    queue<int> q;
    q.push(1);
    d[0] = 0;
    d[1] = 1;

    while (!q.empty())
    {
        int x = q.front();
        q.pop();
        for (int i = head[x]; ~i; i = e[i].next)
        {
            int v = e[i].to;
            if (d[v] > d[x] + 1)
            {
                d[v] = d[x] + 1;
                q.push(v);
                f[v][0] = x;
                for (int j = 1; j < LN; ++j)
                    f[v][j] = f[f[v][j - 1]][j - 1];
                mic[v] = min(mic[v], e[i].w);
            }
        }
    }
}
int dft = 0;
void gdfn(int x, int fa)
{
    dfn[x] = ++dft;
    mic[x] = min(mic[x], mic[fa]);
    for (int i = head[x]; ~i; i = e[i].next)
    {
        int v = e[i].to;
        if (v == fa)
            continue;
        gdfn(v, x);
    }
}
signed main()
{
    std::ios::sync_with_stdio(false);
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    cin >> n;
    memset(head, -1, sizeof head);
    memset(d, 127, sizeof d);
    memset(mic, 127, sizeof mic);
    memset(f, 0, sizeof f);
    mic[1] = 0x3f3f3f3f;
    for (int i = 1; i < n; ++i)
    {
        int t1, t2, t3;
        cin >> t1 >> t2 >> t3;
        addedge(t1, t2, t3);
        addedge(t2, t1, t3);
    }
    gf();

    gdfn(1, 0);
    cin >> m;
    while (m--)
    {
        cin >> k;
        init();
        for (int i = 1; i <= k; ++i)
        {
            cin >> a[i];
            cho[a[i]] = 1;
        }

        build();
        int ans = 0;
        for (int i = hv[1]; ~i; i = ev[i].next)
        {
            int v = ev[i].to;
            dfs(v);
            ans += min(dp[v], mic[v]);
        }
        cout << ans << endl;
    }
    return 0;
}

2025/7/1 19:27
加载中...