• 【模拟退火】poj2069 Super Star


    题意:让你求空间内n个点的最小覆盖球。

    模拟退火随机走的时候主要有这几种走法:①随机旋转角度。

    ②直接不随机,往最远的点的方向走,仅仅在尝试接受解的时候用概率。(最小圆/球覆盖时常用)

    ③往所有点的方向的总和走,仅仅在尝试接受解的时候用概率。(费马点时常用)

    像这题,我用第一种最暴力的随机,死活过不了……

    #include<cstdio>
    #include<cmath>
    #include<algorithm>
    #include<cstdlib>
    using namespace std;
    const double EPS=0.00000001;
    const double PI=acos(-1.0);
    struct Point{
    	double x,y,z;
    	Point(const double &x,const double &y,const double &z){
    		this->x=x;
    		this->y=y;
    		this->z=z;
    	}
    	Point(){}
    	void read(){
    		scanf("%lf%lf%lf",&x,&y,&z);
    	}
    	double length(){
    		return sqrt(x*x+y*y+z*z);
    	}
    }a[35],p,allp;
    double ans,allans;
    int n;
    typedef Point Vector;
    Vector operator - (const Point &a,const Point &b){
    	return Vector(a.x-b.x,a.y-b.y,a.z-b.z);
    }
    Vector operator + (const Vector &a,const Vector &b){
    	return Vector(a.x+b.x,a.y+b.y,a.z+b.z);
    }
    Vector operator * (const double &K,const Vector &v){
    	return Vector(K*v.x,K*v.y,K*v.z);
    }
    double calc(Point p){
    	double res=0.0;
    	for(int i=1;i<=n;++i){
    		res=max(res,(a[i]-p).length());
    	}
    	return res;
    }
    //double ran(){
    //	int fm=rand()%10000+1;
    //	return ((rand()&1) ? -1.0 : 1.0)*((double)(rand()%(fm+1))/(double)fm);
    //}
    Vector unit(Vector v){
    	double l=v.length();
    	return Vector(v.x/l,v.y/l,v.z/l);
    }
    int main(){
    	srand(233);
    	//freopen("poj2069.in","r",stdin);
    	while(1){
    		scanf("%d",&n);
    		if(!n){
    			return 0;
    		}
    		allans=100000.0;
    		for(int i=1;i<=n;++i){
    			a[i].read();
    		}
    //		for(int j=1;j<=n;++j){
    			p=a[1];
    			ans=calc(p);
    			double T=sqrt(20000.0);
    			while(T>EPS){
    				double bestnow=100000.0;
    				Point besttp;
    //				for(int i=1;i<=30;++i){
    //					double rad=(double)(rand()%10000+1)/10000.0*2.0*PI;
    					int to;
    					double far=0.0;
    					for(int k=1;k<=n;++k){
    						double tmp=(a[k]-p).length();
    						if(tmp>far){
    							far=tmp;
    							to=k;
    						}
    					}
    					Point tp=p+T*unit(a[to]-p);
    					double now=calc(tp);
    					if(now<bestnow){
    						bestnow=now;
    						besttp=tp;
    					}
    //				}
    				if(bestnow-100000.0<-EPS && (bestnow<ans || exp((ans-bestnow)/T)*10000.0>(double)(rand()%10000))){
    					ans=bestnow;
    					p=besttp;
    				}
    				T*=0.99;
    			}
    			if(ans<allans){
    				allans=ans;
    //				allp=p;
    			}
    //		}
    		printf("%.5lf
    ",fabs(allans));
    	}
    	return 0;
    }
  • 相关阅读:
    第22章 Makefile基础
    第 36 章 TCP/IP协议基础
    socket通信
    移植zlib
    GNU Autotool介绍
    移植sqlite
    关于wireshark的使用
    关于UDP通信的参考目录
    线程问题
    大数据核心知识点:Hbase、Spark、Hive、MapReduce概念理解,特点及机制
  • 原文地址:https://www.cnblogs.com/autsky-jadek/p/7528342.html
Copyright © 2020-2023  润新知