matrix
Time Limit: 6000/3000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 340 Accepted Submission(s): 208
Problem Description
Given a matrix with
n
rows and
m
columns (
n+m
is an odd number ), at first , you begin with the number at top-left corner (1,1) and you want to go to the number at bottom-right corner (n,m). And you must go right or go down every steps. Let the numbers you go through become an array
a
1
,a
2
,...,a
2k![]()
. The cost is
a
1
∗a
2
+a
3
∗a
4
+...+a
2k−1
∗a
2k![]()
. What is the minimum of the cost?
Input
Several test cases(about
5
)
For each cases, first come 2 integers, n,m(1≤n≤1000,1≤m≤1000)
N+m is an odd number.
Then follows n
lines with
m
numbers
a
i
,j(1≤a
i
≤100)
For each cases, first come 2 integers, n,m(1≤n≤1000,1≤m≤1000)
N+m is an odd number.
Then follows n
Output
For each cases, please output an integer in a line as the answer.
Sample Input
2 3 1 2 3 2 2 1 2 3 2 2 1 1 2 4
Sample Output
4 8
题意:应该都能看懂,就不再翻译了
思路:刚开始看,没想到dp,写完才发现,因为dp弱,所以推了好久,因为只能向右或者向下,所以下一步的状态是由上一步来的,dp数组记录了到达那个点的ans最小值,然后一步一步推,相当于记忆化,在起点的时候该点dp值为0,周围边界直接处理为INF。
在奇数步的时候:转移方程为:dp[i][j]=min(dp[i-1][j],dp[i][j-1]);
在偶数步的时候:转移方程为:dp[i][j]=min(dp[i-1][j]+map[i-1][j]*map[i][j],dp[i][j-1]+map[i][j-1]*map[i][j]);
ac代码:
#include<stdio.h>
#include<string.h>
#include<math.h>
#include<iostream>
#include<algorithm>
#define MAXN 10000001
#define fab(a) (a)>0?(a):(-a)
#define INF 0xfffffff
#define LL long long
#define mem(x) memset(x,0,sizeof(x))
using namespace std;
int map[1010][1010];
LL dp[1010][1010];
int n,m;
int main()
{
int i,j;
while(~scanf("%d%d",&n,&m))
{
for(i=1;i<=n;i++)
{
for(j=1;j<=m;j++)
scanf("%d",&map[i][j]);
}
for(i=0;i<=n+1;i++)
{
for(j=0;j<=m+1;j++)
dp[i][j]=INF;
}
dp[1][1]=0;
for(i=1;i<=n;i++)
{
for(j=1;j<=m;j++)
{
if(i==1&&j==1)
continue;
if((i+j)%2==0)
dp[i][j]=min(dp[i-1][j],dp[i][j-1]);
else
dp[i][j]=min(dp[i-1][j]+map[i-1][j]*map[i][j],dp[i][j-1]+map[i][j-1]*map[i][j]);
}
}
printf("%lld\n",dp[n][m]);
}
return 0;
}