卧薪尝胆,厚积薄发。
国家集训队 种树
Date: Wed Sep 12 08:41:20 CST 2018 In Category: NoCategory

Description:

一圈数,不能选相邻的,问最大和。
$1\le n \le 200000$

Solution:

CTSC2007数据备份 ,只是改成环了,用循环链表就可以了。

Code:


#include<algorithm>
#include<iostream>
#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<queue>
#include<cstring>
using namespace std;
int n,m;
#define MAXN 200010
int val[MAXN];
int lef[MAXN],rig[MAXN];
#define fi first
#define se second
bool v[MAXN];
int main()
{
scanf("%d%d",&n,&m);
if(m * 2 > n)
{
puts("Error!");
return 0;
}
for(int i = 1;i <= n;++i)scanf("%d",&val[i]);
for(int i = 1;i <= n;++i)
{
lef[i] = i - 1;rig[i] = i + 1;
}
lef[1] = n;rig[n] = 1;
priority_queue< pair<int,int> > q;
for(int i = 1;i <= n;++i)
{
q.push(make_pair(val[i],i));
}
int ans = 0;
memset(v,false,sizeof(v));
for(int i = 1;i <= m;)
{
pair<int,int> k = q.top();q.pop();
if(v[k.se])continue;
ans += k.fi;++i;
val[k.se] = val[lef[k.se]] + val[rig[k.se]] - val[k.se];
v[lef[k.se]] = true;v[rig[k.se]] = true;
rig[lef[lef[k.se]]] = k.se;lef[k.se] = lef[lef[k.se]];
lef[rig[rig[k.se]]] = k.se;rig[k.se] = rig[rig[k.se]];
q.push(make_pair(val[k.se],k.se));
}
cout << ans << endl;
return 0;
}
Copyright © 2020 wjh15101051
ღゝ◡╹)ノ♡