题解:AT_arc211_c [ARC211C] Forest
Skyler_yunxi · · 题解
题意:
::::info[本文对题面的修改]
把原串
给定一个长度为
询问:设最大价值和为
Solution
显然,我们把
这样将序列简化完以后,就可以将操作表示为:找到两个类型为
考虑贪心策略,每次只删除一个形如
那么容易发现,为了将序列清空且每次只能删相邻两个
因此我们记全局最大值为
::::success[Code]
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define ull unsigned ll
const int N=5e5+5;
char s[N];
int n,m,r[N];
struct node{int tp,x;ll cnt;}t[N];
int main(){
scanf("%d",&n);
for(int i=1;i<=n;++i)
cin>>s[i];
int mx(0),cnt(0);
s[0]='&';
for(int i=1;i<=n;++i){
scanf("%d",&r[i]);
if(s[i]!=s[i-1]){
if(i!=1){
if(s[i]=='#')t[++m]={0,mx,cnt};
else t[++m]={1,mx,0};
}
mx=r[i],cnt=1;
}
else if(mx<r[i])mx=r[i],cnt=1;
else if(mx==r[i])++cnt;
}
if(s[n]=='#')t[++m]={1,mx,0};
else t[++m]={0,mx,cnt};
int tx(0);
ll ans(0);
for(int i=1;i<=m-2;++i)
if(t[i].tp==0)tx=max(tx,max({t[i].x,t[i+1].x,t[i+2].x}));
for(int i=1;i<=m-2;++i)
if(t[i].tp==0&&max({t[i].x,t[i+1].x,t[i+2].x})==tx)ans+=t[i].cnt*t[i+2].cnt;
printf("%lld",ans);
return 0;
}
::::