華為筆試題:最短路徑問題---出差遇上大霧
阿新 • • 發佈:2019-01-04
問題描述
思路分析
- 這個題其實就是求最短路徑的問題,常見的演算法有兩種,dijkstra演算法和floyd演算法
- 在本例中使用的是後者floyd演算法,時間複雜度O(N^3),空間複雜度O(N^2)
- 使用它的原因是因為,這個演算法十分之優雅,核心程式碼只有五行,寫起來暢快無比。
程式碼展示
package com.huawei.test; import java.util.ArrayList; import java.util.Scanner; public class Demo7 { // 兩個陣列,一個用來儲存任意兩個城市的最短距離,一個用來儲存路徑 private static Integer[][] dist; private static Integer[][] path; // 定義不可達的距離為1000 private final static int INF = 1000; public static void main(String[] args) { int beginCity = 5 - 1;// 出發城市 int size = 6; Scanner sc = new Scanner(System.in); int endCity = sc.nextInt() - 1;// 因為儲存在陣列中,所以要減一 int foggyCity = sc.nextInt() - 1;// 因為儲存在陣列中,所以要減一 // 初始矩陣,表示各個城市之間的距離 Integer[][] matrix = { { 0, 2, 10, 5, 3, INF }, { INF, 0, 12, INF, INF, 10 }, { INF, INF, 0, INF, 7, INF }, { 2, INF, INF, 0, 2, INF }, { 4, INF, INF, 1, 0, INF }, { 3, INF, 1, INF, 2, 0 } }; // 初始化那兩個陣列 dist = new Integer[size][size]; path = new Integer[size][size]; // 設定起霧城市 if (foggyCity != 0) { setFoggyCity(foggyCity, matrix); } // 使用floyd演算法 floyd(matrix); // 距離 System.out.println(dist[beginCity][endCity]); // 路徑 ArrayList<Integer> list = new ArrayList<>(); findPath(beginCity, endCity, list); // 路徑每個值加1 for (int i = 0; i < list.size(); i++) { list.set(i, list.get(i) + 1); } if (dist[beginCity][endCity] == INF) { list.removeAll(list); } System.out.println(list); } // 除錯,m沒有呼叫該函式,不懂的可以用這個函式列印陣列dist\path就會清除了 public static void printMatrix(Integer[][] matrix) { for (int i = 0; i < matrix.length; i++) { for (int j = 0; j < matrix.length; j++) System.out.print(matrix[i][j] + " "); System.out.println(); } } private static void findPath(int beginCity, int endCity, ArrayList<Integer> list) { list.add(beginCity); while (path[beginCity][endCity] != -1) { int midCity = path[beginCity][endCity]; list.add(midCity); beginCity = midCity; } list.add(endCity); } /** * 最核心的輔助函式 * * @param matrix */ private static void floyd(Integer[][] matrix) { int size = matrix.length; // 為輔助陣列賦值 for (int i = 0; i < size; i++) { for (int j = 0; j < size; j++) { dist[i][j] = matrix[i][j]; path[i][j] = -1; } } // floyd演算法 for (int k = 0; k < size; k++) { for (int i = 0; i < size; i++) { for (int j = 0; j < size; j++) { if (dist[i][j] > dist[i][k] + dist[k][j]) { dist[i][j] = dist[i][k] + dist[k][j]; path[i][j] = k; } } } } } // 設定起霧城市 private static void setFoggyCity(int foggyCity, Integer[][] matrix) { for (int i = 0; i < matrix.length; i++) { matrix[i][foggyCity] = INF; matrix[foggyCity][i] = INF; } } }