问题描述
有一条长为n的走廊,小明站在走廊的一端,每次可以跳过不超过p格,每格都有一个权值wi。
小明要从一端跳到另一端,不能回跳,正好跳t次,请问他跳过的方格的权值和最大是多少?输入格式
输入的第一行包含两个整数n, p, t,表示走廊的长度,小明每次跳跃的最长距离和小明跳的次数。
接下来n个整数,表示走廊每个位置的权值。输出格式
输出一个整数。表示小明跳过的方格的权值和的最大值。
样例输入
8 5 3
3 4 -1 -100 1 8 7 6样例输出
12
上面的问题 :我们相当于初始位置在0处,要调到下标8以后
解决动态规划问题的四个步骤:
1. 状态定义
定义一个二维数组dp[ i ][ j ] 表示跳了j下处于i的位置上,存储到达该位置的最大权和值
2. 状态间的转移方程定义dp[i ][ j]=max(dp[i][j] ,dp[i-k][j-1]+v[i])
//从i-k的位置跳了k步到达i的位置上面
3. 状态的初始化
dp[i][1]=v[i]; i<=p
4. 返回结果dp[n+1][t] 在n+1的位置上搜寻距离p的位置的到的结果最多,结果必定会在此处
int main()
{
int n,p,t;
while(cin>>n>>p>>t)
{
//用于保存长度为n的走廊的权值
vector<int> v(n+2,0);
for(int i=1;i<=n;++i)
{
cin>>v[i];
}//状态初始化
vector< vector<long long> > dp(n+2,vector<long long>(t+1,INT_MIN) );
for(int i=1;i<=p&&i<=n+1;++i) //防止p>n,数组越界的情况
{
dp[i][1]=v[i];
}
for(int j=2;j<=t;++j)
{
for(int i=1;i<=n+1;++i)
{
for(int k=1;k<=p&&i-k>0;++k)
{
dp[i][j]=max(dp[i][j],dp[i-k][j-1]+v[i]);
}
}
}
cout<<dp[n+1][t]<<endl;
}
return 0;
}
注:如果本篇博客有任何错误和建议,欢迎伙伴们留言,你快说句话啊!