제출 #50845

#제출 시각아이디문제언어결과실행 시간메모리
50845NicksechkoEvacuation plan (IZhO18_plan)C++14
100 / 100
1150 ms49156 KiB
#include <bits/stdc++.h>

using namespace std;

#define F first
#define S second
#define mp make_pair
#define pb push_back
#define sz(x) ((int)((x).size()))
#define all(x) (x).begin(),(x).end()
#define deb(x) cerr << "(" << #x << " = " << x << ")\n";

typedef long long ll;
typedef pair<int,int> PII;
typedef pair<ll,ll> PLL;
typedef vector<int> VI;

const int MAXN = 100100;
const int MAXA = 100100;
const int MAXB = 100100;
const int INF = 1e9;
const int LOGN = 17;

int n, m, A, B;
vector < PII > g[MAXN];
vector < int > gr[MAXN];
int bad[MAXA];
PII ev[MAXB];
int id[MAXN];
int sh[MAXN];
set < PII > q;

inline bool cmp(int i, int j) {
	return sh[i] > sh[j];
}

void dijkstra() {

	while(!q.empty()) {
		int v = q.begin() -> S;
		q.erase(q.begin());
		for(int i = 0; i < sz(g[v]); ++i) {
			int to = g[v][i].F;
			int w = g[v][i].S;
			if(sh[to] > sh[v] + w) {
				q.erase( mp(sh[to], to) );
				sh[to] = sh[v] + w;
				q.insert( mp(sh[to], to) );
			}
		}
	}
}

int p[MAXN];
int sz[MAXN];

inline int Find(int v) {
	return v == p[v] ? v : p[v] = Find(p[v]);
}

inline void Uni(int a, int b) {
	if(sz[a] >= sz[b])
		p[b] = a, sz[a] += sz[b];
	else
		p[a] = b, sz[b] += sz[a];
}

int tin[MAXN];
int tout[MAXN];
int timer;
int up[MAXN][LOGN + 5];
int mn[MAXN][LOGN + 5];

void dfs(int v, int p = 0) {
	tin[v] = ++timer;
	up[v][0] = p;
	mn[v][0] = sh[v];
	for(int i = 1; i <= LOGN; ++i) {
		up[v][i] = up[up[v][i-1]][i-1];
		mn[v][i] = min(mn[v][i-1], mn[up[v][i-1]][i-1]);
	}
	for(int to : gr[v]) {
		if(to != p) {
			dfs(to, v);
		}
	}
	tout[v] = ++timer;
}

inline bool upper(int a, int b) {
	return tin[a] <= tin[b] && tout[a] >= tout[b];
}

inline int lca(int a, int b) {
	if(upper(a, b)) return a;
	if(upper(b, a)) return b;
	for(int i = LOGN; i >= 0; --i) {
		if(up[a][i] != 0 && !upper(up[a][i], b)) {
			a = up[a][i];
		}
	}
	return up[a][0];
}

int calc(int a, int b) {
	if(a == b) return sh[a];
	int c = lca(a, b);
	int res = INF;
	for(int i = LOGN; i >= 0; --i) {
		if(up[a][i] != 0 && !upper(up[a][i], c)) {
			res = min(res, mn[a][i]);
			a = up[a][i];
		}
		if(up[b][i] != 0 && !upper(up[b][i], c)) {
			res = min(res, mn[b][i]);
			b = up[b][i];
		}
	}
	res = min(res, mn[a][0]);
	res = min(res, mn[b][0]);
	res = min(res, sh[c]);
	return res;
}

int main() {
    ios_base::sync_with_stdio(0);
    cin.tie(0);

    cin >> n >> m;
    for(int i = 1; i <= m; ++i) {
    	int x, y, z;
    	cin >> x >> y >> z;
    	g[x].pb( mp(y, z) );
    	g[y].pb( mp(x, z) );
    }

    for(int i = 1; i <= n; ++i) {
    	sh[i] = INF;
    	id[i] = i;
    }

    cin >> A;
    for(int i = 1; i <= A; ++i) {
    	cin >> bad[i];
    	q.insert( mp(sh[bad[i]] = 0, bad[i]) );
    }
    dijkstra();
    sort(id + 1, id + n + 1, &cmp);

    for(int i = 1; i <= n; ++i) {
    	p[i] = i, sz[i] = 1;
    }
    for(int it = 1; it <= n; ++it) {
    	int i = id[it];
		for(PII j : g[i]) {
			if(sh[j.F] >= sh[i] && Find(i) != Find(j.F)) {
				Uni(Find(i), Find(j.F));
				gr[i].pb(j.F);
				gr[j.F].pb(i);
			}
		}
    }
    sh[0] = INF;
    dfs(1);

    ll ans = 0;
    cin >> B;
    for(int i = 1; i <= B; ++i) {
    	int x, y;
    	cin >> x >> y;
    	cout << calc(x, y) << endl;
    }

    return 0;
}

컴파일 시 표준 에러 (stderr) 메시지

plan.cpp: In function 'int main()':
plan.cpp:166:8: warning: unused variable 'ans' [-Wunused-variable]
     ll ans = 0;
        ^~~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...