github.com/qiuhoude/go-web@v0.0.0-20220223060959-ab545e78f20d/algorithm/datastructures/dp/matrix_min_dist_test.go (about) 1 package dp 2 3 import ( 4 "fmt" 5 "testing" 6 ) 7 8 /* 9 矩阵最短距离 10 11 { 12 {1,3,5,9} 13 {2,1,3,4} 14 {5,2,6,7} 15 {6,8,4,3} 16 } 17 18 求解左上到右下点最短距离, 每一步只能往右 或 下走 19 20 思路: 到 (i,j) 状态的最小值,只能由(i-1,j) 或 (i,j-1) 两个状态转变过来 21 minDis[i][j]= m[i][j] + min(m[i][j-1], m[i-1][j]) 22 */ 23 24 // 回溯法的写法 i表示纵轴, j 表示横轴 25 func minDistBacktracing(i, j, dis int, m [][]int, ret *int) { 26 maxY := len(m) - 1 27 maxX := len(m[0]) - 1 28 if i == maxY && j == maxX { 29 if *ret > dis+m[maxY][maxX] { 30 *ret = dis + m[maxY][maxX] 31 } 32 return 33 } 34 if j < maxX { // 向左走 35 minDistBacktracing(i, j+1, dis+m[i][j], m, ret) 36 } 37 if i < maxY { // 向下走 38 minDistBacktracing(i+1, j, dis+m[i][j], m, ret) 39 } 40 } 41 42 // 动态规划的方式 43 func minDistDp(m [][]int) int { 44 yl := len(m) 45 xl := len(m[0]) 46 47 dp := make([][]int, yl) 48 for i := range dp { 49 dp[i] = make([]int, xl) 50 51 } 52 dp[0][0] = m[0][0] 53 // 设置初始首行和首列的状态 54 for i := 1; i < yl; i++ { //首列 55 dp[i][0] = dp[i-1][0] + m[i][0] 56 } 57 for j := 1; j < xl; j++ { // 首行 58 dp[0][j] = dp[0][j-1] + m[0][j] 59 } 60 61 for i := 1; i < yl; i++ { 62 for j := 1; j < xl; j++ { 63 dp[i][j] = m[i][j] + min(dp[i][j-1], dp[i-1][j]) 64 } 65 } 66 // 倒推路径 67 printPath(yl-1, xl-1, m, dp) 68 return dp[yl-1][xl-1] 69 } 70 71 func printPath(y int, x int, m [][]int, dp [][]int) { 72 fmt.Printf("(%v,%v,%v)", y, x, m[y][x]) 73 for y > 0 && x > 0 { 74 switch dp[y][x] - m[y][x] { 75 case dp[y-1][x]: 76 y-- 77 case dp[y][x-1]: 78 x-- 79 } 80 fmt.Printf("<-(%v,%v,%v)", y, x, m[y][x]) 81 } 82 fmt.Printf("<-(%v,%v,%v)\n", 0, 0, m[0][0]) 83 } 84 85 func min(a, b int) int { 86 if a > b { 87 return b 88 } 89 return a 90 } 91 92 func TestMinDis(t *testing.T) { 93 m := [][]int{ 94 {1, 3, 5, 9}, 95 {2, 1, 3, 4}, 96 {5, 2, 6, 7}, 97 {6, 8, 4, 3}, 98 //{6, 8, 4, 23}, 99 } 100 101 ret := 0x7fffffff 102 minDistBacktracing(0, 0, 0, m, &ret) 103 t.Log(ret) 104 105 ret2 := minDistDp(m) 106 t.Log(ret2) 107 108 }