Title Link https://ajax.loj.ac/problem/10064
Meaning: give you n points, m edges, and connect any selected edges. It is a legal scheme to ensure that the shortest path from point 1 to any point after connecting the edges is the same as that from point 1 to that point after connecting all m edges. The number of schemes was counted and 31 times - 1 of 2 was modeled.
Solution: this question is really a comparative metaphysics. Let's run dijkstra on one side and find the shortest path from point 1 to any point. Then we sort the dis value from small to large, and then use the idea of prim to enumerate and add the nodes to the T-set. If the p-node satisfies dis[p]=dis[x]+v[x][p](v is the length of the edge, X is in the T-set), then the number of schemes in the current step is + 1. Finally, we get the result through the multiplication principle.
#include<cstdio> #include<cstring> #include<cmath> #include<algorithm> #include<queue> #define pr pair < int , int > using namespace std; priority_queue< pr, vector< pr > , greater< pr > > q; const long long mo=(1LL<<31)-1; int cnt,n,m,head[2000000],nxt[2000000],to[2000000],val[2000000],p[2000000],vis[2000000],dis[1000005]; bool f[2000000]; struct xy{ int dis,id; }e[2000000]; bool cmp(xy x,xy y) { return x.dis<y.dis; } void add(int x,int y,int z) { cnt++;nxt[cnt]=head[x];to[cnt]=y;val[cnt]=z;head[x]=cnt; } void dijkstra() { for (int i=1;i<=n;i++) e[i].dis=1000000000; memset(vis,0,sizeof(vis)); e[1].dis=0; q.push(make_pair(0,1)); while (q.size()) { int x=q.top().second;q.pop(); if (vis[x]) continue; vis[x]=1; for (int i=head[x];i;i=nxt[i]) { int y=to[i],z=val[i]; if (e[y].dis>e[x].dis+z) {e[y].dis=e[x].dis+z;q.push(make_pair(e[y].dis,y));} } } } int main() { scanf("%d%d",&n,&m); int x,y,z; for (int i=1;i<=m;i++) { scanf("%d%d%d",&x,&y,&z); add(x,y,z); add(y,x,z); } dijkstra(); for (int i=1;i<=n;i++) e[i].id=i,dis[i]=e[i].dis; sort(e+1,e+n+1,cmp); memset(f,false,sizeof(f)); f[1]=true; for (int i=2;i<=n;i++) { f[e[i].id]=true; for (int j=head[e[i].id];j;j=nxt[j]) { y=to[j]; if (f[y] && dis[y]+val[j]==e[i].dis) p[i]++; } } long long ans=1; for (int i=2;i<=n;i++) ans=(ans*p[i])%mo; printf("%lld\n",ans); }