[Usaco2010 Feb]Chocolate Giving 最短路dijkstra+堆优化

本人水平有限,题解不到为处,请多多谅解

本蒟蒻谢谢大家观看

题目传送门

最短路板子题:迪杰斯特拉+堆优化

注意:因为我建的是大根堆,所以要将距离取负,存入大根堆堆中,这样队首就是最小值。

dijkstra与SPFA还有一个区别是dijkstra的标记数组时根节点不能先标记访问过,否则到后面直接会把根节点continue;距离直接为初始化的最大值,不会遍历树了。

直接套模板即可

code:

 1 #include<bits/stdc++.h>
 2 #define inf 0x3f3f3f3f
 3 #pragma GCC optimize(3)
 4 const int N=50005;
 5 const int M=200002;
 6 using namespace std;
 7 int n,m,B;
 8 int tot;
 9 int ver[M],nxt[M],head[N],edge[M];
10 int dis[N];
11 int opt,ch;
12 bool flag[N];
13 priority_queue< pair<int,int> >q;//第一个是距离,第二个是节点编号 
14 inline int read(){
15     int x=0,f=1;char ch=getchar();
16     while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
17     while(isdigit(ch)){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
18     return x*f;
19 }
20 inline void write(int x)
21 {
22     if(x<0)x=-x,putchar('-');
23     if(x>9)write(x/10);
24     putchar(x%10+'0');
25 }
26 void add(int x,int y,int z){
27     ++tot;
28     ver[tot]=y;
29     edge[tot]=z;
30     nxt[tot]=head[x];
31     head[x]=tot;
32 }
33 void dij(){
34 //    memset(dis,0x3f,sizeof(dis));
35 //    memset(flag,0,sizeof(flag));
36     for(int i=1;i<=n;i++){
37         dis[i]=inf;//因为求最短距离,所以距离初始最大 
38         flag[i]=0;//所有点最开始都没有访问 
39     }//初始化 
40     dis[1]=0;//以1为根的点初始距离为0  
41     q.push(make_pair(0,1));//以1为根的初始距离0入队,节点编号1也入队   注意:flag[1]不能标记为true
42     while(q.size()){//当堆不为空时,才能访问 
43         int x=q.top().second;//x为队首节点编号 
44         q.pop();//取出x 
45         if(flag[x])continue;//如果x先前已经访问过了,就不需要继续访问了 
46         flag[x]=true;//否则就访问x,并把x打上已访问的标记 
47         for(int i=head[x];i;i=nxt[i]){
48             int y=ver[i],z=edge[i];
49             if(dis[y]>dis[x]+z){//若根节点到y的距离大于到x的距离+当前的距离 
50                 dis[y]=dis[x]+z;//更新,求最小值 
51                 q.push(make_pair(-dis[y],y));//入堆 
52             }
53         }
54     }
55 }
56 int main()
57 {
58     n=read(),m=read(),B=read();
59     for(int i=1,x,y,z;i<=m;i++){
60         x=read(),y=read(),z=read();
61         add(x,y,z);
62         add(y,x,z);
63     }
64     dij();
65     while(B--){
66         ch=read(),opt=read();
67         printf("%d
",dis[ch]+dis[opt]);//依据题意 
68     }
69     return 0;
70 }
原文地址:https://www.cnblogs.com/nlyzl/p/11766288.html