这题可以两种写法:
#include<bits/stdc++.h> using namespace std; #define pb push_back const int inf=0x3f3f3f3f; const int maxn=3e5+5; struct edge{int v,w;edge(int a,int b){v=a,w=b;}};//v终点,w边权 struct node{ int id,dis;//id点编号 dis暂时距离 node(int a,int b){id=a,dis=b;} friend bool operator<(node a,node b){ return a.dis>b.dis;//每次让距离小出队 } }; vector<edge>e[maxn]; int dis[maxn];//记录最短路 bool done[maxn];//记录是否找到最短路 int n,m; void dijkstra(){ int s=1;//s起点 根据情况改 for(int i=0;i<=n;i++)dis[i]=inf,done[i]=0; dis[s]=0; priority_queue<node>Q; Q.push(node(s,0)); while(!Q.empty()){ node u=Q.top();Q.pop(); if(done[u.id])continue; done[u.id]=1; for(int i=0;i<e[u.id].size();i++){//遍历邻居 edge y=e[u.id][i]; if(done[y.v])continue; if(dis[y.v]>y.w+dis[u.id]){ dis[y.v]=y.w+u.dis; Q.push(node(y.v,dis[y.v]));//更新最短路 } } } } int main(){ cin>>n>>m; while(m--){ int a,b,c; scanf("%d %d %d",&a,&b,&c); e[a].pb(edge(b,c)); if(a!=b)e[b].pb(edge(a,c)); } dijkstra(); int ans=0,cnt; for(int i=1;i<=n;i++){ cnt=0; for(int j=0;j<e[i].size();j++){ int y=e[i][j].v; if(dis[i]==dis[y]+e[i][j].w)cnt++; if(i>=y&&dis[i]<dis[y]+e[i][j].w&&dis[y]<dis[i]+e[i][j].w)ans++; } if(cnt>1)ans++; } cout<<ans<<endl; return 0; }
第二种方法:
比较鬼。
最短路前驱为1,不炸。
最短路前驱>=2,会少炸x-1次
原文:https://www.cnblogs.com/littlerita/p/12590363.html