HDU 1874 最直接的最短路径问题

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1874

Problem Description
某省自从实行了很多年的畅通工程计划后,终于修建了很多路。不过路多了也不好,每次要从一个城镇到另一个城镇时,都有许多种道路方案可以选择,而某些方案要比另一些方案行走的距离要短很多。这让行人很困扰。
现在,已知起点和终点,请你计算出要从起点到终点,最短需要行走多少距离。
Input
本题目包含多组数据,请处理到文件结束。 每组数据第一行包含两个正整数N和M(0<N<200,0<M<1000),分别代表现有城镇的数目和已修建的道路的数目。城镇分别以0~N-1编号。 接下来是M行道路信息。每一行有三个整数A,B,X(0<=A,B<N,A!=B,0<X<10000),表示城镇A和城镇B之间有一条长度为X的双向道路。 再接下一行有两个整数S,T(0<=S,T<N),分别代表起点和终点。
Output
对于每组数据,请在一行里输出最短需要行走的距离。如果不存在从S到T的路线,就输出-1.
在这道题中因为数据量不大,所以用四种最短路径的方法都可以对它进行求解,也用这道题来令自己熟悉一下四种最短路径的算法:
Dijkstra:
 1 #include <cstdio>
 2 #include <algorithm>
 3 #include<queue>
 4 #include<cstring>
 5 using namespace std;
 6 typedef pair<int,int> pii;
 7 #define N 205
 8 #define M 1005
 9 #define MAXN 0x3f3f3f3f
10 int y[M],d[M],next[M];
11 int first[N],dp[N];
12 int k;
13 
14 //写完函数后这两句话老是忘记写,所以还是这样一开始就写在一个函数里这样自己就不会忘了
15 void init()
16 {
17     k=0;
18     memset(first,-1,sizeof(first));
19 }
20 void add(int a,int b,int c)
21 {
22     y[k]=b,d[k]=c,next[k]=first[a];
23     first[a]=k;
24     k++;
25 }
26 
27 void dijkstra(int src)
28 {
29     priority_queue<pii,vector<pii>,greater<pii> > q;
30     memset(dp,0x3f,sizeof(dp));
31     dp[src]=0,q.push(make_pair(0,src));
32     while(!q.empty()){
33         while(!q.empty()&&dp[q.top().second]<q.top().first) q.pop();
34         if(q.empty()) break;
35         int u=q.top().second;
36         q.pop();
37         for(int i=first[u];i!=-1;i=next[i]){
38             if(dp[y[i]]>dp[u]+d[i]){
39                 dp[y[i]]=dp[u]+d[i];
40                 q.push(make_pair(dp[y[i]],y[i]));
41             }
42         }
43     }
44 }
45 
46 int main()
47 {
48     int n,m,a,b,c,s,t;
49     while(scanf("%d%d",&n,&m)!=EOF){
50         init();
51         for(int i=0;i<m;i++){
52             scanf("%d%d%d",&a,&b,&c);
53             add(a,b,c);
54             add(b,a,c);
55         }
56         scanf("%d%d",&s,&t);
57         dijkstra(s);
58         if(dp[t]<MAXN) printf("%d\n",dp[t]);
59         else printf("%d\n",-1);
60     }
61 
62     return 0;
63 }
View Code

 

SPFA:
 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <queue>
 5 using namespace std;
 6 #define MAXN 20010
 7 #define N 205
 8 int v[MAXN],d[MAXN],next[MAXN],first[N],visit[N],dp[N];
 9 int k;//k表示路的条数
10 
11 void add(int x,int y,int a)//这里添加的是无向图的边,所以进行两次
12 {
13     v[k]=y;
14     next[k]=first[x];
15     d[k]=a;
16     first[x]=k;
17     k++;
18     v[k]=x;
19     next[k]=first[y];
20     d[k]=a;
21     first[y]=k;
22     k++;
23 }
24 
25 int spfa(int a,int b)
26 {
27     memset(dp,0x3f,sizeof(dp));
28     //memset(visit,0,sizeof(visit));//这一段是没有必要的,每次spfa做完,他都会最后变为0
29     queue<int> q;
30     dp[a]=0,visit[a]=1;
31     q.push(a);
32     while(!q.empty()){
33         int c=q.front();
34         q.pop();
35         visit[c]=0;
36         for(int i=first[c];i!=-1;i=next[i]){
37             if(dp[v[i]]>dp[c]+d[i]){
38                 dp[v[i]]=dp[c]+d[i];
39                 if(!visit[v[i]]) q.push(v[i]),visit[v[i]]=1;
40             }
41         }
42     }
43     if(dp[b]<0x3f3f3f3f) return dp[b];
44     else return -1;
45 }
46 
47 int main()
48 {
49     int n,m,start,End,x,y,a;
50     while(scanf("%d%d",&n,&m)!=EOF){
51         k=0;
52         memset(next,-1,sizeof(next));
53         memset(first,-1,sizeof(first));
54         for(int i=0;i<m;i++){
55             scanf("%d%d%d",&x,&y,&a);
56             add(x,y,a);
57         }
58         scanf("%d%d",&start,&End);
59         printf("%d\n",spfa(start,End));
60     }
61     return 0;
62 }
View Code


Floyd:

在使用Floyd时应该把矩阵每个点一开始做好初始化,主对角线上均为0;

其他定位一个最大值。

PS:这道题比较坑的地方是两地间可以有多条路,我们要判断是否为较小的路放入矩阵中

floyd是基于建立在2维矩阵中的,每次更新出一个到达 i 的最短路径,都要遍历一次矩阵,把所有其他节点到 i 点最小值不断更新出来,因为这道题城镇数目比较少,可以采取这种

复杂度为O(n^3)的方法,但是通过这个方法我们可以确定任意一点到其他点的最短路径(自我感觉类似于打表法,有木有?!),不像SPFA做一次只能找到你所需的最短路径

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <algorithm>
 5 using namespace std;
 6 #define N 205
 7 #define MAXN 0x3f3f3f3f
 8 int mat[N][N];
 9 
10 void Floyd(int n)//为n*n的矩阵
11 {
12     for(int i=0;i<n;i++){
13         for(int j=0;j<n;j++){
14             for(int k=0;k<n;k++){
15                 if(mat[j][k]>mat[j][i]+mat[k][i])
16                     mat[j][k]=mat[j][i]+mat[k][i];//i只是用来计更新次数的,实际上每更新一次,都要将整个矩阵的所有点都遍历一遍
17                 }                                 //所以是mat[j][k];
18         }
19     }
20 }
21 int main()
22 {
23     int n,m,start,End,x,y,a;
24     while(scanf("%d%d",&n,&m)!=EOF){
25         memset(mat,0x3f,sizeof(mat));
26         for(int i=0;i<n;i++) mat[i][i]=0;
27         for(int i=0;i<m;i++){
28             scanf("%d%d%d",&x,&y,&a);
29             a=min(a,mat[x][y]);
30             mat[x][y]=a,mat[y][x]=a;//在这里要判断一下,因为两地之间可以有多条路,我们需要判断它到底是否为我们要的最短路
31         }
32         scanf("%d%d",&start,&End);
33         Floyd(n);
34         if(mat[start][End]<MAXN) printf("%d\n",mat[start][End]);
35         else printf("-1\n");
36     }
37     return 0;
38 }
View Code


BellMan-ford:

在写BellMan时,没必要写first[]数组了

它执行一次只能找到固定对应的a到b的最短距离,在这一点上是远远不如Floyd的,而且复杂度为O(n*k),在数据量特别大时是不适用的

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <algorithm>
 5 using namespace std;
 6 #define N 205
 7 #define M 20005
 8 #define MAXN 0x3f3f3f3f
 9 int u[M],v[M],d[M],k;
10 int dp[N];
11 void add(int x,int y,int a)
12 {
13     u[k]=x,v[k]=y,d[k]=a;
14     k++;
15 }
16 void BellMan(int n,int src)
17 {
18     memset(dp,0x3f,sizeof(dp));
19     dp[src]=0;
20     for(int i=0;i<n;i++)
21     {
22         for(int j=0;j<k;j++)
23             if(dp[v[j]]>dp[u[j]]+d[j])
24                 dp[v[j]]=dp[u[j]]+d[j];
25     }
26 }
27 int main()
28 {
29     int n,m,start,End,x,y,a;
30     while(scanf("%d%d",&n,&m)!=EOF){
31         k=0;
32         for(int i=0;i<m;i++){
33             scanf("%d%d%d",&x,&y,&a);
34             add(x,y,a);
35             add(y,x,a);
36         }
37         scanf("%d%d",&start,&End);
38         BellMan(n,start);
39         if(dp[End]<MAXN) printf("%d\n",dp[End]);
40         else printf("-1\n");
41     }
42     return 0;
43 }
View Code

 

转载于:https://www.cnblogs.com/CSU3901130321/p/3873601.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/359674.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

晶体管

晶体管-沟道 场效应-电容性的控制沟道 势效应-直接控制沟道 平带电压 由于半导体和金属的功函数的不同&#xff0c;导致半导体表面层并不属于平带状态&#xff0c;为了恢复平带状态所加的电压为平带电压&#xff0c;Vfb 转载于:https://www.cnblogs.com/rice808/p/3874597.html…

领域驱动设计模式设计与实践_在域驱动设计中使用状态模式

领域驱动设计模式设计与实践域驱动设计&#xff08;DDD&#xff09;是一种开发软件的方法&#xff0c;其中&#xff0c;通过将实现与核心业务概念的不断发展的模型相联系&#xff0c;解决了问题的复杂性。 该术语是由Eric Evans创造的&#xff0c;并且有一个DDD专用站点可以促进…

html 英文文字纵向排列,CSS几种简单方法实现文字竖向排版

1.一个句子的竖向排列如图&#xff1a;1.2. test.one {width: 20px;margin: 0 auto;line-height: 24px;font-size: 20px;}.two {width: 15px;margin: 0 auto;line-height: 24px;font-size: 20px;word-wrap: break-word;/*英文的时候需要加上这句&#xff0c;自动换行*/}我是竖列…

jstree 节点拖拽保存数据库

需要jstree具有拖拽功能需要在加载jstree时添加dnd插件&#xff0c;具体看代码&#xff1a; $(**).jstree({//plugins-各种jstree的插件引入&#xff0c;展示树的多样性 plugins : [ "dnd", "types", "wholerow" ], core : {"check_callbac…

html js utf8编码转换,js 编码转换 gb2312 和 utf8 互转的2种方法

方法一:function gb2utf8(data){var glbEncode [];gb2utf8_data data;execScript("gb2utf8_data MidB(gb2utf8_data, 1)", "VBScript");var tescape(gb2utf8_data).replace(/%u/g,"").replace(/(.{2})(.{2})/g,"%$2%$1").replace(/…

向其他进程注入代码的三种方法

如何向其他线程的地址空间中注入代码并在这个线程的上下文中执行之&#xff1f; 目录&#xff1a;●导言●Windows 钩子&#xff08;Hooks&#xff09;●CreateRemoteThread 和LoadLibrary 技术○进程间通讯●CreateRemoteThread 和 WriteProcessmemory 技术○如何使用该技术子…

自动添加html结束标志,HTML:包含或排除可选的结束标记?

MYYA我在这里添加一些链接来帮助您了解HTML的历史&#xff0c;以便您了解各种矛盾。这不是你的问题的答案&#xff0c;但在阅读这些各种摘要后你会知道更多。我们是怎么来到这里的&#xff1f; - 潜入HTML5网络历史HTML简史HTML的历史 - HTML WG WikiDive Into HTML5的一些摘录…

JAR清单类路径不仅适用于Java Application Launcher

自从我开始学习Java以来​​&#xff0c;我几乎已经知道&#xff0c; 清单文件中的Class-Path标头字段为可执行JAR &#xff08;具有由另一个称为Main-Class清单指定应用程序起点的 JAR&#xff09;指定相对运行时类路径。 一个同事最近碰到一个让我感到惊讶&#xff0c;因为它…

[原创]ActionScript3游戏中的图像编程(连载五)

总目录&#xff1a;http://www.cnblogs.com/iloveas/p/3879125.html 1.1.2 Flash中的ARGB模式与不透明度的关系 ARGB是Flash&#xff0c;svg等矢量处理软件特有的一种色彩模式&#xff0c;事实上我觉得它有点扯淡&#xff0c;A&#xff08;alpha&#xff09;不应该作为一个通道…

通过url,获取html内容,并解析,如何使用 JavaScript 解析 URL

在 Web 开发中&#xff0c;有许多情况需要解析 URL&#xff0c;这篇主要学习如何使用 URL 对象实现这一点。开始创建一个以下内容的 HTML 文件&#xff0c;并在浏览器中打开。JavaScript URL parsing// 激动人心的代码即将写在这里如果你想尝试本文中的任何内容&#xff0c;可以…

define 汉字 error C2001: newline in constant

这个问题真的很让我头大&#xff0c;搜了很多办法都不行&#xff0c;问题是我之前也遇到过&#xff0c;但是编码转为utf-8 unsignature就行了&#xff0c;这次把编码从gb转为utf-8 unsignature 却不行。于是想看看cocos2d-x库文件的编码格式&#xff0c;发现用的是utf-8&#x…

solaris安装java_Solaris是出色的Java开发平台的原因

solaris安装java几天前&#xff0c;我发布了“ OpenSolaris的死亡&#xff1a;为Java开发人员选择操作系统 ”&#xff0c;其中我说Solaris是Java开发人员的绝佳平台。 这篇文章的重点只是想知道自OpenSolaris淘汰以来我将使用哪个Solaris版本。 正如Neil的评论使我意识到的那样…

正确使用计算机说课稿,《计算机结构原理初步》说课稿

在教师招聘考试的过程中&#xff0c;高中信息说课稿的难度就在于如何处理理论与实践的关系&#xff0c;希望这篇《计算机结构原理初步》说课稿能给予你帮助。各位考官大家好!我是号考生&#xff0c;今天我说课的题目是《计算机结构原理初步》。现代教学理论认为&#xff0c;在教…

stringstream实例

stringstream的具体作用稍后来总结&#xff0c;这里分享一个实例&#xff0c;从txt文档中读取数据&#xff0c;并对进行处理。 #include <iostream> #include <sstream> //stringstream的头文件 #include <fstream> #include <vector> #include <s…

计算机2013知识,2013年全国计算机一级考试B基本知识点五

基础5单元格操作对已建立的工作表&#xff0c;根据需要可以编辑修改其中的数据首先要移动单元格指针到目的地或选定编辑对象&#xff0c;然后才能进行增、删、改操作。1.单元格指针的移动要编辑某单元格&#xff0c;必须把单元格指针移动到该单元格&#xff0c;使之成为当前单元…

两种解决IE6不支持固定定位的方法

有两种让IE6支持position:fixed1.用CSS执行表达式 *{margin:0;padding:0;} * html,* html body{ background-image:url(about:blank);background-attachment:fixed; } * html .fixed{position:absolute;bottom:auto;top:expression(eval(document.documentElement.scrollTopdoc…

smartgwt_高级SmartGWT教程,第1部分

smartgwt贾斯汀&#xff08;Justin&#xff09;&#xff0c;帕特&#xff08;Pat&#xff09;和我已经开始着手进行一个需要管理和管理用户界面的副项目。 在与SmartGWT和GWT共同工作了一段时间之后&#xff0c;我们决定使用SmartGWT创建接口。 我们非常喜欢视觉组件&#xff0…

计算机英语女人英语怎么说,英语时差:计算机和女人

00:0000:00微信扫码登陆&#xff0c;畅听全站所有音频&#xff01;(20秒后自动关闭)X关注后&#xff0c;点此关闭https://online2.tingclass.net/lesson/shi0529/10000/10183/67.mp3https://image.tingclass.net/statics/js/2012When you hear the term, "computer geek,&…

Python 生成账号密码算法

有个需求&#xff0c;需要伪造跟用户行为非常类似的账号密码&#xff0c;而且需要一个阀值控制伪造的数量。 在这需求上&#xff0c;还有一个就是需要控制生成的比率、跳出率不能过高或者太低。 对此就随手用python写了一个&#xff0c;bug不知道有木有&#xff0c;没有测&…

云计算系统是大规模计算机系统吗,云计算的系统架构及技术探析

云计算技术属于计算机技术的一种&#xff0c;是目前计算机技术中应用以及研究重点之一&#xff0c;那么云计算到底是什么呢&#xff1f;云计算是在并行处理&#xff0c;分析式处理等技术的基础上发展而来的新技术&#xff0c;可以有效的将计算机进行整合&#xff0c;建立新颖的…