习题:A Twisty Movement (DP)
Posted loney-s
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了习题:A Twisty Movement (DP)相关的知识,希望对你有一定的参考价值。
题目
思路
注意题目中的最后一段话
这意味这选出的序列可以不是连续的
之后我们考虑最后的答案长什么样子
因为只能反转一次
所以最后的答案一定是由4个部分组成
[1111(cdots)] [222(cdots)] [111(cdots) ] [222(cdots) ]
如果没有可以看成空序列
之后就直接暴力DP搞就行了
(dp_{i,j})表示前(i)个数,前(j)个部分的最大值
(egin{cases}dp_{i,1}=dp_{i-1,1}+(a_i==1)\dp_{i,2}=max(dp_{i,1},dp_{i-1,2}+(a_i==2)\dp_{i,3}=max(dp_{i,2},dp_{i-1,3}+(a_i==1)\dp_{i,4}=max(dp_{i,3},dp_{i-1,4}+(a_i==2)end{cases})
很明显第一维是可以省略的
然而空间本来就够,所以省不省都无所谓了
代码
#include<iostream>
using namespace std;
int n;
int a[2005];
int dp[2005][5];
int main()
{
cin>>n;
for(int i=1;i<=n;i++)
cin>>a[i];
for(int i=1;i<=n;i++)
{
dp[i][1]=dp[i-1][1]+(a[i]==1);
dp[i][2]=max(dp[i][1],dp[i-1][2]+(a[i]==2));
dp[i][3]=max(dp[i][2],dp[i-1][3]+(a[i]==1));
dp[i][4]=max(dp[i][3],dp[i-1][4]+(a[i]==2));
}
cout<<dp[n][4];
return 0;
}
以上是关于习题:A Twisty Movement (DP)的主要内容,如果未能解决你的问题,请参考以下文章
Codeforces 934C - A Twisty Movement
Codeforces-462C. A Twisty Movement
[Codeforces 933A]A Twisty Movement