HDU 1385 Minimum Transport Cost

  • 我的WA代码
  • AC的代码

我的WA代码

我的大概思路就是,如果i->j,如果找到一个中间点k就直接简单的将path[i][j]=k,这样我们在遍历的时候就可以直接找到中间点k,然后通过一个递归的中序遍历的到i->k再到k->j这条路径。但是错了!!!

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Scanner;public class Main {private final static int INF = 9999999;// flodyprivate final static int[][] flody(int[][] map, int[] city, int n) {int[][] path = new int[n+1][n+1];for(int i=1;i<=n;i++) {Arrays.fill(path[i], -1);}int tmp;for(int k=1;k<=n;k++) {for(int i=1;i<=n;i++) {if(map[i][k] == INF)continue;for(int j=1;j<=n;j++) {tmp = map[i][k] + map[k][j]+city[k];if(map[i][j] > tmp) {map[i][j] = tmp;path[i][j] = k;}else if(map[i][j] == tmp && path[i][j] > k) {path[i][j] = k;}}}}return path;}private final static void printFlody(int[][] path, int s, int e) {System.out.println(String.format("From %d to %d :", s, e));if(s == e) {System.out.println(String.format("Path: %d", s));return;}System.out.print(String.format("Path: %d-->", s));ArrayList<Integer> list = new ArrayList<>();middle(list, path, s, e);for(Integer u : list) {System.out.print(String.format("%d-->", u));}System.out.println(e);}private final static void middle(ArrayList<Integer> list, int[][] path, int i, int j) {int k = path[i][j];if(k == -1)return;middle(list, path, i, k);list.add(k);middle(list, path, k, j);}public static void main(String[] args) {Scanner sc = new Scanner(System.in);int n;int[][] map;int[] city;int s, e;while(true) {n = sc.nextInt();if(n == 0) {break;}map = new int[n+1][n+1];for(int i=1;i<=n;i++) {for(int j=1;j<=n;j++) {map[i][j] = sc.nextInt();if(map[i][j] == -1)map[i][j] = INF;}}city = new int[n+1];for(int i=1;i<=n;i++) {city[i] = sc.nextInt();}int[][] flody = flody(map, city, n);while(true) {s = sc.nextInt();e = sc.nextInt();if(s == -1 && e == -1) {break;}printFlody(flody, s, e);System.out.println(String.format("Total cost : %d", map[s][e]));System.out.println();}}sc.close();}
}

AC的代码

于是最后AC的代码就改了一下,人家的思路是这样的!!!没太看的明白,不过语义上的理解就是:

  1. 首先,如果有一条直通的边,就直接简单的将路径设置为“目的点”。
  2. 如果遇到一个“中间点”,那么我们将记录i->j的“起始点”,这个起始点是path[k][j]
  3. 上面两条语义合起来看,就能够明白大致的意思:path[i][j]记录的是i->j的第一个节点
  4. 假设i->j第一个节点为k,那么接下来我们只需要知道k->j的路径了
  5. 一直重复第4步操作,最后到k==j停止
import java.util.Scanner;public class Main {private final static int INF = 9999999;// flodyprivate final static int[][] flody(int[][] map, int[] city, int n) {int[][] path = new int[n+1][n+1];for(int i=1;i<=n;i++) {for(int j=1;j<=n;j++) {if(map[i][j] != INF) {path[i][j] = j;}}}int tmp;for(int k=1;k<=n;k++) {for(int i=1;i<=n;i++) {if(map[i][k] == INF)continue;for(int j=1;j<=n;j++) {tmp = map[i][k] + map[k][j]+city[k];if(map[i][j] > tmp) {map[i][j] = tmp;path[i][j] = path[i][k];}else if(map[i][j] == tmp && path[i][j] > path[i][k]) {path[i][j] = path[i][k];}}}}return path;}private final static void printFlody(int[][] path, int s, int e) {System.out.println(String.format("From %d to %d :", s, e));System.out.print(String.format("Path: %d", s));while(s!=e) {System.out.print(String.format("-->%d", path[s][e]));s = path[s][e];}System.out.println();}public static void main(String[] args) {Scanner sc = new Scanner(System.in);int n;int[][] map;int[] city;int s, e;while(true) {n = sc.nextInt();if(n == 0) {break;}map = new int[n+1][n+1];for(int i=1;i<=n;i++) {for(int j=1;j<=n;j++) {map[i][j] = sc.nextInt();if(map[i][j] == -1)map[i][j] = INF;}}city = new int[n+1];for(int i=1;i<=n;i++) {city[i] = sc.nextInt();}int[][] flody = flody(map, city, n);while(true) {s = sc.nextInt();e = sc.nextInt();if(s == -1 && e == -1) {break;}printFlody(flody, s, e);System.out.println(String.format("Total cost : %d", map[s][e]));System.out.println();}}sc.close();}
}

HDU 1385 Minimum Transport Cost相关推荐

  1. 【floyd存字典序路径】【HDU1385】【Minimum Transport Cost】

    题目大意 求多组i到j的最短路径 并输出字典序最小.... 现在只会floyd的方式 利用dis[i][j] 表示i到j的路径中i 后面的节点 更新是比较dis[i][j] dis[i][k]. 记住 ...

  2. [floyd+路径输出]HDU1385 Minimum Transport Cost

    题目链接 题目翻译: 有N个城市,然后直接给出这些城市之间的邻接矩阵,矩阵中-1代表那两个城市无道路相连,其他值代表路径长度. 如果一辆汽车经过某个城市,必须要交一定的钱(可能是过路费). 现在要从a ...

  3. hdu 5511 Minimum Cut-Cut——分类讨论思想+线段树合并

    题目:http://acm.hdu.edu.cn/showproblem.php?pid=5511 题意:割一些边使得无向图变成不连通的,并且恰好割了两条给定生成树上的边.满足非树边两段一定在给定生成 ...

  4. HDU 1394 Minimum Inversion Number(线段树的单点更新)

    点我看题目 题意 :给你一个数列,a1,a2,a3,a4.......an,然后可以求出逆序数,再把a1放到an后,可以得到一个新的逆序数,再把a2放到a1后边,,,,,,,依次下去,输出最小的那个逆 ...

  5. hdu 3473 Minimum Sum 划分树

    http://acm.hdu.edu.cn/showproblem.php?pid=3473 对于xl,xl+1--xr,使得[xi-x]和最小,显然x应当为其中的中位数.中位数可以通过求K大数解决, ...

  6. HDU 3473 Minimum Sum 【划分树】

    题目来源:http://acm.hdu.edu.cn/showproblem.php?pid=3473 ★没想到划分树里面也可以加东西,wcsl 题意: 给你一个由n个数组成的序列,有m次询问,每次询 ...

  7. HDU 4408 Minimum Spanning Tree 最小生成树计数

    http://acm.hdu.edu.cn/showproblem.php?pid=4408 题意:求最小生成树个数 题解:对于Kruskal算法,我们发现,最小生成树要想用多种方法就要有长度相同的边 ...

  8. HDU - 4280 Island Transport(最大流)

    题目链接:点击查看 题目大意:给出n个岛屿,由m条无向边连接而成,现在要从最西边的岛屿到达最东边的岛屿,问最大流量为多少 题目分析:最大流模板题,只不过这个毒瘤题卡掉了dinic,只能去网上找了个SA ...

  9. HDU - 5452 Minimum Cut(LCA+树上差分)

    题目链接:点击查看 题目大意:给出n个点,n-1条边组成一棵树,然后再给出m-n-1条边,组成一个图,现在要让我们求最少删去几条边才能让整个图不连通,并且要求只能在树上删去最多一条边 题目分析:这个题 ...

最新文章

  1. 2022-2028年中国复合软管行业市场行情动态及发展趋向分析报告
  2. 一个关于小程序Iot的具体实现(MQTT版)
  3. LeetCode 2129. 将标题首字母大写
  4. 操作文件 -------JavaScrip
  5. lua --- 表操作
  6. Hi3519V101开发环境搭建(二)
  7. matlab编写识别手写数字_使用PYNQ搭建手写数字识别工程小白级说明(完整版)
  8. webpack4搭建vue
  9. 大数据实战之环境搭建(十)
  10. 高德坐标转百度坐标并导航
  11. pdf2swf process阻塞问题
  12. 凯恩帝数控系统面板介绍_凯恩帝数控车床操作面板按钮详解!
  13. 前端数据可视化插件(一)图表
  14. 运放参数的详细解释和分析-压摆率(SR)
  15. 第五章-对单词进行分类和标记
  16. 我为什么离开华为加入ThoughtWorks(思特沃克)
  17. 苹果怎么滚动截屏_30个小技巧,带你感受苹果系统到底有多好用
  18. UserBehavior 阿里巴巴淘宝用户行为数据字段分析
  19. [论文笔记] Detection of Glottal Closure Instants from Speech Signals: CNN Method
  20. 软件工程结构化建模的方法和工具_系统架构师之——软件开发方法

热门文章

  1. NYOJ 905 卡片游戏
  2. NYOJ 358 取石子(五)
  3. EasyNVR支持的摄像机、NVR设备接入类型以及关于国标设备是否支持接入EasyNVR无插件流媒体服务器...
  4. Thinkphp的知识内容
  5. {%csrf_token%}的作用
  6. QEMU-KVM中的多线程压缩迁移技术
  7. Jenkins默认工作空间及更改默认工作空间
  8. poj 1020 深搜
  9. NPOI读取Excel模板并向其中写入数据
  10. “熊猫烧香”式的病毒营销