题目传送门
算法:前缀和
我们用pre[i]表示前个石头的差值
用sum[i]表示从第i个到第n个石头的差值
当pre[i]==sum[i+1]时,表示不用交换就可以完成任务
如果不相等我们交换a[i]和a[i+1]
再来比较a[i]-pre[i-1]和a[i+1]-sum[i+2]是否相等,如果相等说明交换后可以完成任务
贴上代码
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll inf=1e9+5;
const int N=2e5+5;
ll pre[N],sum[N];
ll a[N];
int main()
{
int t;
cin>>t;
while(t--)
{
int flag=0;
memset(pre,0,sizeof pre);
memset(sum,0,sizeof sum);
int n;
cin>>n;
for(int i=1;i<=n;i++) cin>>a[i];
for(int i=1;i<=n;i++)
{
if(a[i]>=pre[i-1]) pre[i]=a[i]-pre[i-1];
else pre[i]=inf/2;
}
for(int i=n;i>=1;i--)
{
if(a[i]>=sum[i+1]) sum[i]=a[i]-sum[i+1];
else sum[i]=inf;
}
for(int i=1;i<n;i++)
{
if(pre[i]==sum[i+1])
{
flag=1;
break;
}
else
{
ll tmp1=a[i];
ll tmp2=a[i+1];
if(tmp1>=sum[i+2]&&tmp2>=pre[i-1])
{
tmp2-=pre[i-1];
tmp1-=sum[i+2];
if(tmp1==tmp2)
{
flag=1;
break;
}
}
}
}
if(flag) puts("YES");
else puts("NO");
}
return 0;
}