萌新刚学模拟退火一天求助
查看原帖
萌新刚学模拟退火一天求助
227728
冰糖鸽子「僕は…」楼主2021/5/2 11:05

RT,被奇怪的题解和奇怪的讨论弄晕了,现在不知道什么是退火的正确写法了

只混了10pts,而且因为太菜了完全不懂是算法的问题还是参数的问题/dk

如果看见什么弱智错误请轻喷啊/kel,小鸽子真的很菜


// Problem: P5544 [JSOI2016]炸弹攻击1
// Contest: Luogu
// URL: https://www.luogu.com.cn/problem/P5544
// Memory Limit: 250 MB
// Time Limit: 1000 ms
// Powered by CP Editor (https://github.com/cpeditor/cpeditor)

#include <bits/stdc++.h>
using namespace std;
#define M 1005
int nans,rans,ans,n,m,R;
double T0,Tn,Te;
struct node
{
	double x,y,_r;
}cas[M],En[M];
double nx,ny;
double d(node X,node Y)
{
	return sqrt((X.x-Y.x)*(X.x-Y.x)+(X.y-Y.y)*(X.y-Y.y));
}
double Min(double X,double Y)
{
	return (X<Y?X:Y);
}
int CHECK()
{
	int res=0;
	double _R=R,tp;
	for(int i=1;i<=n;i++)
	{
		tp=d(cas[i],node{nx,ny,0})-cas[i]._r;
		if(tp<0) return 0;
		_R=Min(_R,tp);
	}
	for(int i=1;i<=m;i++) res+=(d(En[i],node{nx,ny,0})<=_R);
	return res;
}
int Getrd(int l,int r) {return (rand()%(r-l+1))+l;}
void SA()//模拟退火主要函数
{
	T0=0.999,Tn=1000,Te=1e-10;//温度重置
	int px,py;//坐标偏移量
	while(Tn>Te)
	{
	  	px=Tn*(2*rand()-RAND_MAX);py=Tn*(2*rand()-RAND_MAX);
	  	nx+=px;ny+=py;
	  	nans=CHECK();rans=max(rans,nans);
	  	// cout<<nans<<' '<<nx<<' '<<ny<<endl;
	  	// if(nans) cout<<nans<<' '<<nx<<' '<<ny<<endl;
	  	if(nans>ans) {ans=nans;}//当前解更优
		else if(exp((nans-ans)/Tn)<(double)rand()/RAND_MAX) {ans=nans;}
		else {nx-=px;ny-=py;}
		Tn*=T0;
	}
}
int main()
{
  	srand(time(NULL));
  	cin>>n>>m>>R;
  	for(int i=1;i<=n;i++) cin>>cas[i].x>>cas[i].y>>cas[i]._r;
	for(int i=1;i<=m;i++) {cin>>En[i].x>>En[i].y;nx+=En[i].x;ny+=En[i].y;}
	nx/=m;ny/=m;ans=rans=CHECK();
	// nx=2.9;ny=2.9;ans=rans=CHECK();
	SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();SA();
    cout<<rans;
	return 0;
}
2021/5/2 11:05
加载中...