缩点+lca
大水题。
洛谷恶意评分++
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <iostream> #include <cstdio> #include <vector> #include <cstring> using namespace std; const int N=10005; int n,m,low[N],dfn[N],tim,stk[N],tt,id[N],dep[N],son[N],siz[N],tot,fa[N],top[N]; vector<int>G[N],T[N]; bool ins[N]; void tarjan(int x,int from) { low[x]=dfn[x]=++tim;stk[++tt]=x;ins[x]=1; for(int i=0;i<G[x].size();i++) { int v=G[x][i]; if(v==from) continue; if(!dfn[v]) {tarjan(v,x);low[x]=min(low[x],low[v]);} else if(ins[v]) low[x]=min(low[x],dfn[v]); } if(dfn[x]==low[x]) { ++tot; id[x]=tot;ins[x]=0; while(stk[tt]!=x) ins[stk[tt]]=0,id[stk[tt--]]=tot; tt--; } } void dfs(int x) { siz[x]=1; for(int i=0;i<T[x].size();i++) { int v=T[x][i]; if(v!=fa[x]) {fa[v]=x;dep[v]=dep[x]+1;dfs(v);siz[x]+=siz[v];if(siz[v]>siz[son[x]]) son[x]=v;} } } void dfs(int x,int Top) { top[x]=Top; if(!son[x]) return ; dfs(son[x],Top); for(int i=0;i<T[x].size();i++) { int v=T[x][i]; if(v!=fa[x]&&v!=son[x]) dfs(v,v); } } int lca(int x,int y) { while(top[x]!=top[y]) (dep[top[x]]>=dep[top[y]]?x=fa[top[x]]:y=fa[top[y]]); return dep[x]<dep[y]?x:y; } void print(int x) { if(x) print(x>>1); if(x) putchar('0'+(x&1)); } int main() { scanf("%d%d",&n,&m); for(int i=1,u,v;i<=m;i++) { scanf("%d%d",&u,&v); G[u].push_back(v); G[v].push_back(u); } for(int i=1;i<=n;i++) if(!dfn[i]) tarjan(i,0); for(int i=1;i<=n;i++) { for(int j=0;j<G[i].size();j++) { int v=G[i][j]; if(id[i]!=id[v]) T[id[i]].push_back(id[v]); } } dfs(1); dfs(1,1); scanf("%d",&m); for(int i=1,u,v;i<=m;i++) { scanf("%d%d",&u,&v); int l=lca(id[u],id[v]); if(dep[id[u]]+dep[id[v]]-dep[l]-dep[l]+1==0) {puts("0") ;continue;} print(dep[id[u]]+dep[id[v]]-dep[l]-dep[l]+1); printf(" "); } return 0; }