1. 程式人生 > 實用技巧 >【日常刷題】陣列中一條路線的最大值

【日常刷題】陣列中一條路線的最大值

陣列中一條路線的最大值

tags: [#演算法, #回溯, #動態規劃]

題目

給定一個m*n的陣列,使其從左上角移動至右下角,限定只能向下和向右移動,將經過的數相加,求所有移動路線中相加數為最大的數。

例項

輸入: [[2,3,1], [2,5,3], [4,2,1]]

輸出: 14

想法

菜鳥三思再次記錄自己的菜雞想法:

  • 首先,我判斷了一下是否可以使用貪心演算法。但是很可惜,因為沒有遇見後面的大數,所以在前面也不敢說走哪個方向好,因此不能使用貪心
  • 我打算使用暴力破解,採用了回溯
    • 先一路往下,碰壁後,在往右走
    • 然後發現。。。超時了,即便加上剪枝也依舊超時。
  • 終於在最後的關鍵,想起了大佬的想法動態規劃
    • 建立一個備忘錄,然後自低向上的遍歷陣列。
    • 在陣列每個位置,判斷它是走下面好,還是走右邊好。
    • 同時將走過的資料記錄在備忘錄中。

程式碼

回溯

/**
 * 功能說明: 求陣列左上角至右下角的路線最大值
 *
 * @author sansi
 */
public class Max_Matrix {

	public static void main(String[] args) {
		int[][] matrix = { { 2, 3, 1 }, { 2, 5, 3 }, { 4, 2, 1 } };
		System.out.println(new Max_Matrix().new Solution().maxValue(matrix));
	}

	class Solution {

		public int count = 0;
		public int max = Integer.MIN_VALUE;

		public int maxValue(int[][] matrix) {
			// write code here
			trace(0, 0, matrix);
			return max;
		}


		public void trace(int r, int c, int[][] matrix) { 
			if (r == matrix.length-1) { //回溯至陣列的最後一行
				int tmp = 0; 
				for (int i=c;i<matrix[0].length;i++) { 
					tmp += matrix[r][i]; 
				} 
				if (max < (count + tmp)) { 
					max = count + tmp; 
				} 
				return; 
			} 
			if (c == matrix[0].length-1) { //回溯至陣列的最後一列
				int tmp = 0; 
				for (int i=r;i<matrix.length;i++) { 
					tmp += matrix[i][c]; 
				}
				if (max < (count + tmp)) {
					max = count + tmp; 
				} 
				return; 
			} if (r == matrix.length || c == matrix[0].length) { //越界
				return; 
			}
			if (r < matrix.length) { 
				count += matrix[r][c]; 
				trace(r+1, c, matrix); 
				count -= matrix[r][c]; 
			} 
			if (c < matrix[0].length) { 
				count += matrix[r][c]; 
				trace(r, c+1, matrix); 
				count -= matrix[r][c]; 
			}
		}
	}
}

動態規劃

/**
 * 功能說明: 求陣列左上角至右下角的路線最大值
 *
 * @author sansi
 */
public class Max_Matrix {
	
	public static void main(String[] args) {
		int[][] matrix = {{1,1,1},{1,1,1},{1,1,1}};
		System.out.println(new Max_Matrix().new Solution().maxValue(matrix));
	}

	class Solution {

	    public int[][] dp;//備忘錄
	    
	    public int maxValue (int[][] matrix) {
	        // write code here
	    	dp = matrix;
	        fun(matrix);
	        return dp[0][0];
	    }
	    
	    
	    /**
	     * 動態規劃,回溯見鬼去吧
	     */
	    public void fun(int[][] matrix) {
	    	for (int i=matrix.length-1;i>=0;i--) {
	    		for (int j=matrix[0].length-1;j>=0;j--) {
	    			if (i == matrix.length-1 && j == matrix[0].length-1) {
	    				continue;
	    			}
	    			if (i == matrix.length-1) {
	    				dp[i][j] = dp[i][j] + matrix[i][j+1];
	    				continue;
	    			}
	    			if (j == matrix[0].length-1) {
	    				dp[i][j] = dp[i][j] + matrix[i+1][j];
	    				continue;
	    			}
	    			dp[i][j] = dp[i][j] + (matrix[i+1][j] > matrix[i][j+1] ? matrix[i+1][j] : matrix[i][j+1]);
	    		}
	    	}
	    }
	}
}