PAT (Advanced Level) 1076. Forwards on Weibo (30)
最短路。
每次询问的点当做起点,然后算一下点到其余点的最短路。然后统计一下最短路小于等于L的点有几个。
#include<cstdio> #include<cstring> #include<cmath> #include<vector> #include<map> #include<stack> #include<queue> #include<string> #include<algorithm> using namespace std; const int INF=0x7FFFFFFF; const int maxn=1000+100; struct Edge { int u,v; int dis; }e[200*maxn]; vector<int>g[maxn]; int tot; int flag[maxn],dis[maxn]; int n,L; void SPFA(int s) { queue<int>Q; memset(flag,0,sizeof flag); for(int i=0;i<=n;i++) dis[i]=INF; Q.push(s); flag[s]=1; dis[s]=0; while(!Q.empty()) { int head=Q.front(); Q.pop(); flag[head]=0; for(int i=0;i<g[head].size();i++) { int id=g[head][i]; if(dis[head]+e[id].dis<dis[e[id].v]) { dis[e[id].v]=dis[head]+e[id].dis; if(flag[e[id].v]==0) { flag[e[id].v]=1; Q.push(e[id].v); } } } } } int main() { tot=0; scanf("%d%d",&n,&L); for(int i=1;i<=n;i++) { int m; scanf("%d",&m); while(m--) { int id; scanf("%d",&id); e[tot].u=id; e[tot].v=i; e[tot].dis=1; g[id].push_back(tot); tot++; } } int k; scanf("%d",&k); for(int i=1;i<=k;i++) { int id; scanf("%d",&id); SPFA(id); int ans=0; for(int i=1;i<=n;i++) if(i!=id&&dis[i]<=L) ans++; printf("%d\n",ans); } return 0; }