【USACO】 Max Flow
【题目链接】
【算法】
LCA + 树上差分
【代码】
#include<bits/stdc++.h> using namespace std; int i,x,y,N,K,l,maxn; int anc[50010][50],d[50010],sum[50010]; vector<int> E[50010]; void build(int x,int pre) { int i; for (i = 1; i <= 20; i++) anc[x][i] = anc[anc[x][i-1]][i-1]; for (i = 0; i < E[x].size(); i++) { if (E[x][i] != pre) { anc[E[x][i]][0] = x; d[E[x][i]] = d[x] + 1; build(E[x][i],x); } } } int lca(int x,int y) { int i,f; if (d[x] > d[y]) swap(x,y); f = d[y] - d[x]; for (i = 0; i <= 20; i++) { if (f & (1 << i)) y = anc[y][i]; } if (x == y) return x; for (i = 20; i >= 0; i--) { if (anc[x][i] != anc[y][i]) { x = anc[x][i]; y = anc[y][i]; } } return anc[x][0]; } void query(int x,int pre) { int i; for (i = 0; i < E[x].size(); i++) { if (E[x][i] != pre) { query(E[x][i],x); sum[x] += sum[E[x][i]]; } } maxn = max(maxn,sum[x]); } int main() { cin >> N >> K; for (i = 1; i < N; i++) { cin >> x >> y; E[x].push_back(y); E[y].push_back(x); } build(1,0); for (i = 1; i <= K; i++) { cin >> x >> y; l = lca(x,y); sum[x]++; sum[y]++; sum[l]--; if (anc[l][0]) sum[anc[l][0]]--; } query(1,0); cout<< maxn << endl; return 0; }