BZOJ 4390 [Usaco2015 dec] Max Flow【LCA與樹上差分】
阿新 • • 發佈:2018-11-08
樹上差分板子:
#include <cmath> #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #define db double #define sg string #define ll long long #define rep(i,x,y) for(ll i=(x);i<=(y);i++) #define red(i,x,y) for(ll i=(x);i>=(y);i--) using namespace std; const ll N=5e4+5; const ll Inf=1e18; ll n,m,ans,v[N],dep[N],fa[N][20]; ll cnt,to[N<<1],nxt[N<<1],head[N]; inline ll read() { ll x=0;char ch=getchar();bool f=0; while(ch>'9'||ch<'0'){if(ch=='-')f=1;ch=getchar();} while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();} return f?-x:x; } inline void write(ll x) { if(x<0) putchar('-'); if(x>9) write(x/10); putchar(x%10+48); } void ins(ll x,ll y) { to[++cnt]=y;nxt[cnt]=head[x];head[x]=cnt; } void dfs(ll x) { dep[x]=dep[fa[x][0]]+1; rep(i,1,19) fa[x][i]=fa[fa[x][i-1]][i-1]; for(ll i=head[x];i;i=nxt[i]) { ll y=to[i]; if(y!=fa[x][0]) { fa[y][0]=x;dfs(y); } } } ll lca(ll x,ll y) { if(dep[x]<dep[y]) swap(x,y); ll dlt=dep[x]-dep[y]; rep(i,0,19) if(dlt&(1<<i)) x=fa[x][i]; if(x==y) return y; red(i,19,0) if(fa[x][i]!=fa[y][i]) x=fa[x][i],y=fa[y][i]; return fa[x][0]; } void _dfs(ll x) { for(ll i=head[x];i;i=nxt[i]) { ll y=to[i]; if(y!=fa[x][0]) { _dfs(y);v[x]+=v[y]; } } ans=max(ans,v[x]); } int main() { n=read(),m=read(); rep(i,2,n) { ll x=read(),y=read(); ins(x,y),ins(y,x); } dfs(1); rep(i,1,m) { ll x=read(),y=read(),z=lca(x,y); ++v[x],++v[y]; --v[z],--v[fa[z][0]]; } _dfs(1); write(ans); return 0; }