题目链接:点击查看
题意:Bessie和Elsie在玩一种卡牌游戏。一共有2N张卡牌,点数分别为1到2N,每头牛都会分到N张卡牌。游戏一共分为N轮,因为Bessie太聪明了,她甚至可以预测出每回合Elsie会出什么牌。每轮游戏里,两头牛分别出一张牌,点数大者获胜。同时,Bessie有一次机会选择了某个时间点,从那个时候开始,每回合点数少者获胜。Bessie现在想知道,自己最多能获胜多少轮?
题解:从前向后求个最大的大于的次数,从后向前求最大的小于的次数,枚举位置求个最大值即可。
之前有个疑问就是如果前后用到一个数字a怎么办,假设还有b未用,如果b>a,那么我们就把b替换前面的a,如果b<a,那么我们就替换后面的a,zxf 太强了
#include<bits/stdc++.h>
using namespace std;
set<int> s1,s2;
int n,a[50010];
int dp1[50010],dp2[50010];
int main()
{
scanf("%d",&n);
for(int i=1;i<=n*2;i++)
{
s1.insert(i);
s2.insert(-i);
}
for(int i=1;i<=n;i++)
{
scanf("%d",&a[i]);
s1.erase(a[i]);
s2.erase(-a[i]);
}
for(int i=1;i<=n;i++)
{
int pos=*s1.lower_bound(a[i]);
dp1[i]=dp1[i-1];
if(pos>a[i]) dp1[i]++,s1.erase(pos);
}
int ans=dp1[n];
for(int i=n;i>=1;i--)
{
int pos=*s2.lower_bound(-a[i]);
dp2[i]=dp2[i+1];
if(pos>-a[i]) dp2[i]++,s2.erase(pos);
ans=max(ans,dp1[i-1]+dp2[i]);
}
printf("%d\n",ans);
return 0;
}