日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

动态规划实例(十五):最短路径Floyd

發布時間:2023/12/18 编程问答 50 豆豆
生活随笔 收集整理的這篇文章主要介紹了 动态规划实例(十五):最短路径Floyd 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

? ? 本文參考http://blog.csdn.net/ochangwen/article/details/50730937,

? ? 1.定義概覽
? ? Floyd-Warshall算法(Floyd-Warshall algorithm)又稱為插點法是解決任意兩點間的最短路徑的一種算法,可以正確處理有向圖或負權的最短路徑問題,同時也被用于計算有向圖的傳遞閉包。Floyd-Warshall算法的時間復雜度為O(N3),空間復雜度為O(N2)。
? ??

? ? 2.算法描述:
? ? 1)算法思想原理:
? ? ?Floyd算法是一個經典的動態規劃算法。用通俗的語言來描述的話,首先我們的目標是尋找從點i到點j的最短路徑。從動?態規劃的角度看問題,我們需要為這個目標重新做一個詮釋(這個詮釋正是動態規劃最富創造力的精華所在),?從任意節點i到任意節點j的最短路徑不外乎2種可能,1是直接從i到j,2是從i經過若干個節點k到j。所以,我們假設
Dis(i,j)為節點u到節點v的最短路徑的距離,對于每一個節點k,我們檢查Dis(i,k) + Dis(k,j) < Dis(i,j)是否成立,如果成立,證明從i到k再到j的路徑比i直接到j的路徑
短,我們便設置Dis(i,j) = Dis(i,k) + Dis(k,j),這樣一來,當我們遍歷完所有節點k,Dis(i,j)中記錄的便是i到j的最短路徑的距離。
? ? 2).算法描述:
? ? ? ? a.從任意一條單邊路徑開始。所有兩點之間的距離是邊的權,如果兩點之間沒有邊相連,則權為無窮大。   
? ? ? ? b.對于每一對頂點 u 和 v,看看是否存在一個頂點 w 使得從 u 到 w 再到 v 比己知的路徑更短。如果是更新它。
? ? 3).Floyd算法過程矩陣的計算----十字交叉法
? ? ??

? ?補充其中用到的十字交叉法如下:

? ??先來簡單分析下,由于矩陣中對角線上的元素始終為0,因此以k為中間點時,從上一個矩陣到下一個矩陣變化時,矩陣的第k行,第k列和對角線上的元素是不發生改變的(對角線上都是0,因為一個頂點到自己的距離就是0,一直不變;而當k為中間點時,k到其他頂點(第k行)和其他頂點到k(第k列)的距離是不變的)

? ? 因此每一步中我們只需要判斷4*4-3*4+2=6個元素是否發生改變即可,也就是要判斷既不在第k行第k列又不在對角線上的元素。具體計算步驟如下:以k為中間點(1)“三條線”:劃去第k行,第k列,對角線(2)“十字交叉法”:對于任一個不在三條線上的元素x,均可與另外在k行k列上的3個元素構成一個2階矩陣x是否發生改變與2階矩陣中不包含x的那條對角線上2個元素的和有關,若二者之和小于x,則用它們的和替換x,對應的Path矩陣中的與x相對應的位置用k來替代。。。

? ? 具體實例及代碼如下所示:

/** * @Title: Floyd.java * @Package dynamicprogramming * @Description: TODO * @author peidong * @date 2017-6-13 上午9:23:39 * @version V1.0 */ package dynamicprogramming; /** * @ClassName: Floyd * @Description: 弗洛伊德最短路徑算法 * @date 2017-6-13 上午9:23:39 * */ public class Floyd {public static void shorestFloyd(){int MAX_VALUE = 65535; int[][] edgesMatrix ={{0, 5, MAX_VALUE, 7}, {MAX_VALUE, 0, 4, 2}, {3, 3, 0, 2}, {MAX_VALUE, MAX_VALUE, 1, 0}}; int n = 4;//vertexSize; 結點個數 int[][] tc = new int[n][n]; //保存從i到j的最短路徑值 int[][] p = new int[n][n]; //保存經過的中間結點 //初始化tc,p for(int i = 0; i < n; i++){for(int j = 0; j < n; j++){p[i][j] = -1; tc[i][j] = edgesMatrix[i][j]; //便矩陣 }}//進行Floyd算法,從0到n-1所有可能進行遍歷 for(int x = 0; x < n; x++){ //x表示中間結點 for(int i = 0; i < n; i++){for(int j = 0; j < n; j++){if(tc[i][j] > tc[i][x] + tc[x][j]){tc[i][j] = tc[i][x] + tc[x][j]; p[i][j] = x; }}}}// 下面對獲得的結果進行展示 System.out.println("最短路徑狀態轉移矩陣為:"); for (int i = 0; i < n; i++) {for (int j = 0; j < n; j++) {System.out.print(" " + tc[i][j]); }System.out.println(); }System.out.println("對應的結點矩陣為:"); for (int i = 0; i < n; i++) {for (int j = 0; j < n; j++) {System.out.print(" " + p[i][j]); }System.out.println(); } // System.out.println("+++++++++++++++++++++++++++++++++++"); /* for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) { System.out.println("輸出i=" + i + "到j=" + j + "最短路徑:"); int k = p[i][j]; if (k == -1) { System.out.println("沒有最短路徑"); } else { System.out.print(" " + k); while (k != j) { k = p[k][j]; System.out.print(" " + k); } System.out.println(" "+k); System.out.println(); } } } */ }/** * @Title: main * @Description: 測試用例 * @param args * @return void * @throws */ public static void main(String[] args) {// TODO Auto-generated method stub shorestFloyd(); }}

總結

以上是生活随笔為你收集整理的动态规划实例(十五):最短路径Floyd的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。