被爆金币了,后面 4 个点 RE,数组都开到 3000 了,前面几个点的错误率也挺高的。
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N=3005;
const double eps=1e-8,down=0.9112;
int T,n,s1,s2,ans;
int a[N],a1[N],a2[N];
int get(){
int sum1=0,sum2=0;
for(int i=1;i<=s1;i++)
sum1+=a1[i];
for(int i=1;i<=s2;i++)
sum2+=a2[i];
return abs(sum1-sum2);
}
void SA(){
double temp=50000;
while(temp>eps){
int x=rand()%s1+1;
int y=rand()%s2+1;
swap(a1[x],a2[y]);
int dif=get();
if(dif<ans){
ans=dif;
temp*=down;
continue;
}else if(exp(-dif/temp)*RAND_MAX>rand()){
temp*=down;
continue;
}
temp*=down;
swap(a1[x],a2[y]);//换回来
}
}
signed main(){
srand(time(0));
cin>>T;
while(T--){
memset(a,0,sizeof(a));
memset(a1,0,sizeof(a1));
memset(a2,0,sizeof(a2));
cin>>n;
for(int i=1;i<=n;i++) cin>>a[i];
s1=n/2,s2=n-s1,ans=1e18+7;
for(int i=1;i<=s1;i++) a1[i]=a[i];
for(int i=1;i<=s2;i++) a2[i]=a[i+s1];
int t=50;
while(t--) SA();
cout<<ans<<'\n';
}
return 0;
}