提高組NOIP2007 矩陣取數遊戲

2021-09-05 18:13:33 字數 2040 閱讀 4011

題目描述

帥帥經常跟同學玩乙個矩陣取數遊戲:對於乙個給定的n*m的矩陣,矩陣中的每個元素a[i,j] 均為非負整數。遊戲規則如下:

每次取數時須從每行各取走乙個元素,共n個。m次後取完矩陣所有元素;

每次取走的各個元素只能是該元素所在行的行首或行尾;

每次取數都有乙個得分值,為每行取數的得分之和,每行取數的得分 = 被取走的元素值*2^i,其中i表示第i次取數(從1開始編號);

遊戲結束總得分為m次取數得分之和。帥帥想請你幫忙寫乙個程式,對於任意矩陣,可以求出取數後的最大得分。

輸入

輸入檔案game.in包括n+1行:

第1行為兩個用空格隔開的整數n和m。

第2~n+1行為n*m矩陣,其中每行有m個用單個空格隔開的非負整數。

輸出輸出檔案game.out僅包含1行,為乙個整數,即輸入矩陣取數後的最大得分。

樣例輸入

sample input1:

2 31 2 3

3 4 2

sample input2:

1 44 5 0 5

sample input3:

2 10

96 56 54 46 86 12 23 88 80 43

16 95 18 29 30 53 88 83 64 67

樣例輸出

sample output1:

【輸入輸出樣例1解釋】

第1次:第1行取行首元素,第2行取行尾元素,本次得分為1*21+2*21=6

第2次:兩行均取行首元素,本次得分為2*22+3*22=20

第3次:得分為3*23+4*23=56。總得分為6+20+56=82

sample output2:

sample output3:

資料範圍限制

【限制】

60%的資料滿足:1<=n, m<=30, 答案不超過10^16

100%的資料滿足:1<=n, m<=80, 0<=a[i,j]<=1000

思路:

dp可以發現每一行可以單獨處理,答案就是每一行獲得的最大分數的和。

要高精度,注意常數優化。

#include#pragma gcc optimize(3)

#define open(x) freopen(x".in","r",stdin);freopen(x".out","w",stdout);

#define n 100

#define ll long long

using namespace std;

ll base=1000;

ll work(ll b)

return ans;

}struct bignum

void init()

bool operator < (const bignum &y) const

while(b)

return *this;

} bignum operator +(const bignum b)

if(c.num[tmp+1]>0)c.len=tmp+1;else c.len=tmp;

return c;

}bignum operator *(const ll a)

if(b.num[b.len+3])b.len+=3;else if(b.num[b.len+2])b.len+=2;else if(b.num[b.len+1])b.len+=1;

return b;

} void print() }

}int main()

ans.print();

}

NOIP2007提高組 矩陣取數遊戲

本題dp 高精度即可。首先我們可以發現它的貢獻只與行有關係,於是就分成n行,每行都做dp,然後將max加起來即可。ps 用高精度實現 上標 include include include define mo 100000 define ll long long using namespace std...

NOIP2007提高組 矩陣取數遊戲

本題dp 高精度即可。首先我們可以發現它的貢獻只與行有關係,於是就分成n行,每行都做dp,然後將max加起來即可。ps 用高精度實現 上標 include include include define mo 100000 define ll long long using namespace std...

NOIp2007提高組 矩陣取數遊戲

oj題號 洛谷1005 思路 動態規劃。不難發現每行能夠取得的最大值僅與當前行的資料有關,因此本題可以對每行的資料分別dp,最後求和。設 f 表示左邊取 i 個 右邊取 j 個的最大值,則dp方程為 f max f a 2 f a 2 然而資料規模較大,使用 int 只有40分,用 unsigned...