题意:中文题,他给的半径实际上就是两点之间的距离,然后要求找出两个点的权值加上之间的距离最大。
a数组表示每个点的权值,设两个点分别是i,j,所以答案就是a[i]-i*r+a[j]+j*r,对于一个j应该要找到满足要求最大的a[i]-i*r,所以就用单调队列了,还要注意就是单调队列里相等的话就直接加到队尾,优先取编号小的。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int MAXN=100010;
typedef long long ll;
typedef pair<ll,ll> Point;
int q[MAXN<<1];
ll a[MAXN<<1];
int main()
{
int t,n,i,flag=1;
ll r;
scanf("%d",&t);
while(t--)
{
scanf("%d%lld",&n,&r);
for(i=1;i<=n;i++)
{
scanf("%lld",&a[i]);
a[i+n]=a[i];
}
int front=0,rear=-1;
Point ans;
ll aans=0;
q[++rear]=1;
for(i=2;i<=2*n;i++)
{
while(front<=rear&&(i-q[front])>n/2)
front++;
if(front<=rear&&a[i]+a[q[fro