1. 程式人生 > >洛谷 P2049 魔術棋子

洛谷 P2049 魔術棋子

一個 org i++ using bit print 記得 targe color

P2049 魔術棋子

題目描述

在一個M*N的魔術棋盤中,每個格子中均有一個整數,當棋子走進這個格子中,則此棋子上的數會被乘以此格子中的數。一個棋子從左上角走到右下角,只能向右或向下行動,請問此棋子走到右下角後,模(mod)K可以為幾?

如以下2*3棋盤:

3 4 4

5 6 6

棋子初始數為1,開始從左上角進入棋盤,走到右下角,上圖中,最後棋子上的數可能為288,432或540。所以當K = 5時,可求得最後的結果為:0,2,3。

輸入輸出格式

輸入格式:

輸入文件magic.in第一行為三個數,分別為M,N,K (1 ≤ M,N,K ≤ 100)以下M行,每行N個數,分別為此方陣中的數。

輸出格式:

輸出文件magic.out第一行為可能的結果個數

第二行為所有可能的結果(按升序輸出)

輸入輸出樣例

輸入樣例#1:
Magic.in
2 3 5
3 4 4
5 6 6
輸出樣例#1:
3
0 2 3



背包,用一個三維數組存每個點每個值是否會出現,到最後一個點,出現的情況最多只有k種
代碼中dp[i][j][l*ma[i][j]%k]=dp[i-1][j][l]||dp[i][j-1][l] 表示從它的左邊或上邊是否會傳下l這個值來
要時刻記得%k,防止炸掉

#include<bits/stdc++.h>
using
namespace std; int n,m,k,dp[101][101][101],ma[2333][2333],res[10000000],num; int main() { scanf("%d%d%d",&n,&m,&k); for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) { scanf("%d",&ma[i][j]); ma[i][j]%=k; if(i==1&&j==1
) dp[i][j][ma[i][j]]=1; } for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) for(int l=0;l<k;l++) if(!dp[i][j][l*ma[i][j]%k]) dp[i][j][l*ma[i][j]%k]=dp[i-1][j][l]||dp[i][j-1][l]; for(int i=0;i<k;i++) if(dp[n][m][i]) num++; printf("%d\n",num); for(int i=0;i<k;i++) if(dp[n][m][i]) printf("%d ",i); return 0; }

 

洛谷 P2049 魔術棋子