NC16624. [NOIP2009]道路游戏
描述
输入描述
第一行3个正整数,n,m,p(2≤n≤1000,1≤m≤1000,1≤p≤m),意义如题目所述。
接下来的 n 行,每行有m 个正整数,每两个整数之间用一个空格隔开,其中第i行描述了i号马路上每个单位时间内出现的金币数量(1≤金币数量≤100),即第i行的第j(1≤j≤m)个数表示第j个单位时间内i号马路上出现的金币数量。
最后一行,有 n 个整数,每两个整数之间用一个空格隔开,其中第i个数表示在i号机器人工厂购买机器人需要花费的金币数量(1≤金币数量≤100)。
输出描述
共一行,包含1 个整数,表示在m 个单位时间内,扣除购买机器人花费的金币之后,小新最多能收集到多少金币。
示例1
输入:
2 3 2 1 2 3 2 3 4 1 2
输出:
5
C++14(g++5.4) 解法, 执行用时: 446ms, 内存消耗: 3056K, 提交时间: 2019-10-27 20:53:30
#include<bits/stdc++.h> using namespace std; int n,m,p,ans,tot,a[1007][1007],c[1007],f[1007]; int main() { cin>>n>>m>>p; for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) cin>>a[i][j]; for(int i=1;i<=n;i++) cin>>c[i]; for(int i=1;i<=m;i++) f[i]=-1e9; for(int i=1;i<=m;i++) { for(int j=1;j<=n;j++) { tot=f[i-1]-c[j]; for(int k=0;k<p&&k+i<=m;k++) { int z=j+k,v=i+k; if(z>n)z=z%n; tot+=a[z][v]; f[v]=max(f[v],tot); } } } cout<<f[m]<<endl; return 0; }
C++11(clang++ 3.9) 解法, 执行用时: 374ms, 内存消耗: 2532K, 提交时间: 2020-03-04 21:09:24
#include<bits/stdc++.h> using namespace std; int f[1010][1010],a[1010],dp[1010]; int main() { int n,m,p; cin>>n>>m>>p; for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) cin>>f[i][j]; for(int i=1;i<=n;i++) cin>>a[i]; for(int i=1;i<=m;i++) dp[i]=-2e9; for(int i=1;i<=m;i++) for(int j=1;j<=n;j++) { int ans=dp[i-1]-a[j]; for(int k=0;k<p&&i+k<=m;k++) { ans+=f[(j+k-1)%n+1][i+k]; dp[i+k]=max(dp[i+k],ans); } } cout<<dp[m]<<"\n"; return 0; }