제출 #1315594

#제출 시각아이디문제언어결과실행 시간메모리
1315594cleimek경주 (Race) (IOI11_race)C++20
100 / 100
547 ms41048 KiB
#include "race.h"
#include <bits/stdc++.h>
using namespace std;

typedef long long ll;
const int MAXN = 2e5+7;
const int MAXL = 1e6+7;
const int INF = 1e8+7;

struct Node{
    int to, w;
};

vector<vector<Node>> graph(MAXN,vector<Node>());
vector<bool> is_off(MAXN,false);
vector<int> sub_size(MAXN);
vector<pair<int, int>> minNodes(MAXL,{0, -1});

int res=MAXN;

void GetSubSizes(int v, int p){
    sub_size[v]=1;
    for(auto [u,w] : graph[v]){
        if(is_off[u] || u==p) continue;
        GetSubSizes(u,v);
        sub_size[v] += sub_size[u];
    }
}

int FindCentroid(int v, int p, int tree_size){
    for(auto [u,_] : graph[v]){
        if(is_off[u] || u==p) continue;
        if(sub_size[u] > ((tree_size+1)/2)) return FindCentroid(u,v,tree_size);
    }
    return v;
}

void ResultDFS(int v, int p, int depth, int val, int k, int c){
    if(val > k) return;
    if (minNodes[k-val].second == c) res = res = min(res, minNodes[k-val].first+depth);
    for(auto [u,w] : graph[v]){
        if(is_off[u] || u==p) continue;
        ResultDFS(u,v,depth+1,val+w,k,c);
    }
}

void UpdateDFS(int v, int p, int depth, int val, int k, int c){
    if(val > k) return;
    if (minNodes[val].second == c) minNodes[val] = min(minNodes[val], {depth, c});
    else minNodes[val] = {depth, c};
    for(auto [u,w] : graph[v]){
        if(is_off[u] || u==p) continue;
        UpdateDFS(u,v,depth+1,val+w,k,c);
    }
}

void ProcessCentroid(int centroid, int k){
    minNodes[0]={0, centroid};
    for(auto [u,w] : graph[centroid]){
        if(is_off[u]) continue;
        ResultDFS(u,centroid,1,w,k,centroid);
        UpdateDFS(u,centroid,1,w,k,centroid);
    }
}

void CentroidDecomposition(int v, int k){
    GetSubSizes(v,v);
    int centroid = FindCentroid(v,v,sub_size[v]);
    ProcessCentroid(centroid,k);
    is_off[centroid]=true;
    for(auto [u,_] : graph[centroid]){
        if(is_off[u]) continue;
        CentroidDecomposition(u,k);
    }
}

int best_path(int N, int K, int H[][2], int L[]) {
    int n=N, k = K;
    for(int i=0; i<n-1; ++i) {
        int nodeA = H[i][0], nodeB = H[i][1], weight = L[i];
        graph[nodeA].push_back({nodeB,weight});
        graph[nodeB].push_back({nodeA,weight});
    }
    
    CentroidDecomposition(0,k);
    
    if(res==MAXN) res=-1;
    return res;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...