題面如下:
x 國王有乙個地宮寶庫,是 n×m
'>n×m
個格仔的矩陣,每個格仔放一件寶貝,每個寶貝貼著價值標籤。
地宮的入口在左上角,出口在右下角。
小明被帶到地宮的入口,國王要求他只能向右或向下行走。
走過某個格仔時,如果那個格仔中的寶貝價值比小明手中任意寶貝價值都大,小明就可以拿起它(當然,也可以不拿)。
當小明走到出口時,如果他手中的寶貝恰好是 k
'>k
k 件,則這些寶貝就可以送給小明。
請你幫小明算一算,在給定的局面下,他有多少種不同的行動方案能獲得這 k
'>k
k 件寶貝。
輸入格式
第一行 3
'>3
個整數,n,m
,k'>n,m,k
,含義見題目描述。
接下來 n
'>n
行,每行有 m
'>m
個整數 c
i'>ci
用來描述寶庫矩陣每個格仔的寶貝價值。
輸出格式
輸出乙個整數,表示正好取 k
'>k
個寶貝的行動方案數。
該數字可能很大,輸出它對 1000000007
'>1000000007
取模的結果。
資料範圍1≤
n,m≤
50'>1≤n,m≤501≤
k≤12'>1≤k≤120≤
ci≤12
'>0≤ci≤12
輸入樣例1:
2 2 2
1 22 1
輸出樣例1:2
輸入樣例2:2 3 2
1 2 3
2 1 5
輸出樣例2:
這個題的題目資料範圍很小,可以預估是乙個維數較多的dp,我最開始的思路如下(雖然這個思路不對,但是ac思路是在這個基礎上做了一點很小的調整):
每個點都只能往下或者往右移動,可以選擇拿走下面/右面的寶物,也可以不拿,如果拿了,k維度上公升一層,否則仍然在這一層,同時維護當前手中最大的物品重量就可以了
列舉順序和lintcode114 unique paths等走迷宮類似的題目的列舉順序一樣,一行行計算即可,只不過多加了一重k的限制
起始點寶物的拾取不能按照上述規則處理,所以在最開始單獨給dp[0][0][1]特殊賦值一下
然後開開心心地吃了兩發wa,感覺事情不對勁,突然意識到這個手中最大寶物重量不能直接存個最大的,舉個例子:3,3,3處有5種走法,最大重量是7;2,3,4處有6種走法,最大重量是9,這兩個位置都能來到3,3,4這個位置,雖然方案數看著可以合併,但是他們最大重量是不同的,所以實際上不能直接合併(3,3,4這個點需要記錄著有5種走法的最大重量是7;有6種走法的最大重量是9,不然面臨乙個重量為8的寶物,你是沒辦法處理的),所以。。我們還要再加一層陣列,把它變成四維陣列,其中第四維表示最大重量,這樣我們的dp陣列表示的含義就變成了下面這樣:
dp[i][j][t][p]表示位置在i,j處,當前已經拿了t個物品,這些物品中的最大重量是p的方案個數有多少種,轉移方程沒太大變化,就是加了乙個第四維的迴圈
ac**如下:
#include #include#include
#include
using
namespace
std;
#define modulus 1000000007
long
long arr[55][55][13][14
];int weight[55][55
];int
main()
}arr[
0][0][0][0] = 1
; arr[
0][0][1][weight[0][0]] = 1
;
for(int i = 0; i < n; i++)
if(weight[i][j+1] >p)
}//cout << "i=" << i <
//cout << arr[i][j][t] << endl;
} }
}int sum = 0
;
for(int i = 0; i < 14; i++)
cout
<< sum <
return0;
}
藍橋杯 地宮取寶
x 國王有乙個地宮寶庫,是 n m 個格仔的矩陣,每個格仔放一件寶貝,每個寶貝貼著價值標籤。地宮的入口在左上角,出口在右下角。小明被帶到地宮的入口,國王要求他只能向右或向下行走。走過某個格仔時,如果那個格仔中的寶貝價值比小明手中任意寶貝價值都大,小明就可以拿起它 當然,也可以不拿 當小明走到出口時,...
藍橋杯 地宮取寶 DP
問題描述 x 國王有乙個地宮寶庫。是 n x m 個格仔的矩陣。每個格仔放一件寶貝。每個寶貝貼著價值標籤。地宮的入口在左上角,出口在右下角。小明被帶到地宮的入口,國王要求他只能向右或向下行走。走過某個格仔時,如果那個格仔中的寶貝價值比小明手中任意寶貝價值都大,小明就可以拿起它 當然,也可以不拿 當小...
藍橋杯 地宮取寶 dp
歷屆試題 地宮取寶 時間限制 1.0s 記憶體限制 256.0mb 問題描述 x 國王有乙個地宮寶庫。是 n x m 個格仔的矩陣。每個格仔放一件寶貝。每個寶貝貼著價值標籤。地宮的入口在左上角,出口在右下角。小明被帶到地宮的入口,國王要求他只能向右或向下行走。走過某個格仔時,如果那個格仔中的寶貝價值...