天天看點

數塔 DP

A - 數塔

在講述DP算法的時候,一個經典的例子就是數塔問題,它是這樣描述的: 有如下所示的數塔,要求從頂層走到底層,若每一步隻能走到相鄰的結點,則經過的結點的數字之和最大是多少? 

數塔 DP

 已經告訴你了,這是個DP的題目,你能AC嗎?

Input輸入資料首先包括一個整數C,表示測試執行個體的個數,每個測試執行個體的第一行是一個整數N(1 <= N <= 100),表示數塔的高度,接下來用N行數字表示數塔,其中第i行有個i個整數,且所有的整數均在區間[0,99]内。 Output對于每個測試執行個體,輸出可能得到的最大和,每個執行個體的輸出占一行。 Sample Input

1
5
7
3 8
8 1 0 
2 7 4 4
4 5 2 6 5
           

Sample Output

30
           
數塔 DP
import java.util.Scanner;
import java.util.Arrays;

public class Main {

	static final int MAX = 105;

	public static void main(String[] args) {
		// TODO Auto-generated method stub

		Scanner cin = new Scanner(System.in);
		int[][] a = new int[MAX][MAX];
		int[][] dp = new int[MAX][MAX];
		int t = cin.nextInt();
		while (t-- != 0) {
			int n = cin.nextInt();
			for (int i = 1; i <= n; i++) {
				for (int j = 1; j <= i; j++) {
					a[i][j] = cin.nextInt();
				}
			}
			//對邊界的處理,最後一行,下面沒有元素,初始化為原來的值
			for (int i = 1; i <= n; i++) {
				dp[n][i] = a[n][i];
			}

			for (int i = n - 1; i >= 1; i--) {
				for (int j = 1; j <= i; j++) {
					//除了最後一行每個結點最大為目前結點的值加上左下或右下的值,(通過比較來确定加哪一個)
		            //循環結束後,原始圖變成了最優圖
					dp[i][j] = a[i][j] + Math.max(dp[i + 1][j], dp[i + 1][j + 1]);
				}

			}
			System.out.println(dp[1][1]);//遞歸的終止條件為頂元素

		}
	}
}
           

繼續閱讀