POJ 1062
題意:其實吧,,我也沒看懂題意。。還是說一下dijkstra算法,,三個步驟,循環(huán)n次
while(n--)
{
???? 在所有未標號節(jié)點中,選出d[]值最小的節(jié)點
???? 標記
??? 松弛所有與這個點相關(guān)的所有邊
}
這個算法的精髓在于,每次找到的最小邊都不能被其他節(jié)點松弛,只能它去松弛別的節(jié)點。這樣,就可以打印出來最短路徑的遍歷順序了;換種說法就是,每次找到的那個點,都是最有資格去松弛其他節(jié)點的點,所以最多循環(huán)n次;不可以處理負環(huán)
?
Bellman 的算法:
循環(huán)n-1次,每次將所有的邊松弛一遍;這個算法可以檢查是否有負環(huán),當出現(xiàn)負環(huán)/正環(huán)的時候,還可以繼續(xù)松弛。
?
AC代碼:
?
1 //dijkstla算法 2 #include <stdio.h> 3 #include <string.h> 4 #include <algorithm> 5 #define INF 0x3f3f3f3f 6 using namespace std; 7 int vis[105],edge[105][105],n,price[105],level[105],d[105]; 8 void init() 9 { 10 for(int i=1; i<=n; i++) 11 { 12 for(int j=1; j<=n; j++) 13 { 14 edge[i][j]=INF;//初始化,要求最短路徑,所以先初始化為無窮大 15 } 16 } 17 } 18 void read() 19 { 20 int l,t,tp; 21 for(int i=1; i<=n; i++) 22 { 23 scanf("%d%d%d",&price[i],&level[i],&l); 24 for(int j=0; j<l; j++) 25 { 26 scanf("%d%d",&t,&tp); 27 edge[t][i]=tp;//存儲邊的信息的時候,要將能到達的”優(yōu)惠價格“存起來 28 } 29 } 30 } 31 int dijkstla()//算法主要分三個步驟,循環(huán)n次。1.找出所有節(jié)點中最小的2.標記3.松弛所有的與這個節(jié)點相關(guān)的點。 32 { 33 for(int i=1; i<=n; i++) 34 { 35 d[i]=price[i]; 36 } 37 int pos; 38 for(int i=1; i<=n; i++) 39 { 40 int temp=INF; 41 for(int j=1; j<=n; j++) 42 { 43 if(d[j]<temp&&!vis[j]) 44 { 45 temp=d[j]; 46 pos=j; 47 } 48 } 49 vis[pos]=1; 50 for(int j=1; j<=n; j++) 51 { 52 if(d[j]>d[pos]+edge[pos][j]&&!vis[j]) 53 { 54 d[j]=d[pos]+edge[pos][j]; 55 } 56 } 57 } 58 return d[1]; 59 } 60 int main() 61 { 62 int m,ans; 63 while(~scanf("%d%d",&m,&n)) 64 { 65 init(); 66 read(); 67 ans=INF; 68 for(int i=1; i<=n; i++) 69 { 70 int min1=level[i]; 71 for(int j=1; j<=n; j++) 72 { 73 if(level[j]<min1||level[j]-min1>m) 74 { 75 vis[j]=1; 76 } 77 else 78 { 79 vis[j]=0; 80 } 81 } 82 int now=dijkstla(); 83 ans=min(ans,now); 84 } 85 printf("%d\n",ans); 86 } 87 return 0; 88 } View Code?
轉(zhuǎn)載于:https://www.cnblogs.com/qioalu/p/4709176.html
總結(jié)
- 上一篇: Thread.currentThread
- 下一篇: Linux学习笔记:Linux分区