您的位置:首页 > 其它

jzoj 2047. 对布满灰尘的西洋棋宣告将军

2016-08-17 17:24 274 查看

题目描述

维多利加:这里的确有许多书,但是……

这里没有你。

【问题描述】

布洛瓦侯爵想利用维多利加来占卜二战的局势。侯爵只给了她一盘西洋棋和 许多书,便将她关在了王宫的地牢。

西洋棋盘可以看成一个 N*M 的网格。西洋棋可以摆放在任何一个格子里, 而不是网格线的交叉点上。

维多利加将一个棋子放在了左上角的格子上。她试着移动这个棋子,棋子只 会向右或者向下移动。

每个格子有一个权值,维多利加想知道,从左上角到右下角的所有路径中:

1.经过的格子的权值和最大是多少?

2.权值和最大的路径一共有多少条?

输入

第一行两个整数 N,M。

接下来 N 行,每行 M 个整数,表示每个格子的权值。

输出

输出两行,第一行表示最大权值和,第二行表示权值和最大的路径数除以 1e9+7 的余数。

思路

dp

记录下每次的路径和最大值

#include <stdio.h>
using namespace std;
long long a[2001][2001],f[2001][2001],g[2001][2001];
__attribute__((optimize("O2")))
int main()
{
freopen("chess.in","r",stdin);
freopen("chess.out","w",stdout);
int n,m;
scanf("%d%d",&n,&m);
for (int i=1;i<
d4c6
;=n;i++)
for (int j=1;j<=m;j++)
scanf("%lld",&a[i][j]);
for (int i=1;i<=n;i++)
{
g[1][i]=1;
g[i][1]=1;
f[1][i]=f[1][i-1]+a[1][i];
f[i][1]=f[i-1][1]+a[i][1];
}
for (int i=2;i<=n;i++)
for (int j=2;j<=m;j++)
{
if (f[i-1][j]+a[i][j]>f[i][j-1]+a[i][j])
{
f[i][j]=f[i-1][j]+a[i][j];
g[i][j]=g[i-1][j]%1000000007;
}
else
if (f[i-1][j]+a[i][j]<f[i][j-1]+a[i][j])
{
f[i][j]=f[i][j-1]+a[i][j];
g[i][j]=g[i][j-1]%1000000007;
}
else
{
g[i][j]=(g[i-1][j]+g[i][j-1])%1000000007;
f[i][j]=f[i][j-1]+a[i][j];
}
}
printf("%lld\n",f
[m]);
printf("%lld\n",g
[m]);
fclose(stdin);
fclose(stdout);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: