zoukankan      html  css  js  c++  java
  • 【洛谷4212】外太空旅行(模拟退火)

    点此看题面

    大致题意: 给你一张图,让你从中选取最多的点,使这些点所构成的是完全图。

    模拟退火

    这道题可以用模拟退火来乱搞(或者随机化+(dfs)?)。

    大体就是搞一个序列,定义其价值为从左往右、见到合法点立刻选所能选出的点数。

    然后模拟退火,求出最大价值即为答案。

    代码

    #include<bits/stdc++.h>
    #define Tp template<typename Ty>
    #define Ts template<typename Ty,typename... Ar>
    #define Reg register
    #define RI Reg int
    #define Con const
    #define CI Con int&
    #define I inline
    #define W while
    #define N 50
    #define swap(x,y) (x^=y^=x^=y)
    #define Gmax(x,y) (x<(y)&&(x=(y)))
    using namespace std;
    int n,f[N+5][N+5];
    class SimulatedAnnealing//模拟退火
    {
    	private:
    		#define SA_TIME 100
    		int ans,s[N+5],vis[N+5];
    		I int Calc()//求出序列价值
    		{
    			RI i,j,res=0;for(i=1;i<=n;++i)
    			{
    				for(j=1;j^i;++j) if(vis[j]&&!f[s[i]][s[j]]) break;
    				i^j?vis[i]=0:(++res,vis[i]=1);
    			}return res;
    		}
    		I void Work()//模拟退火
    		{
    			RI i,x,y,res,nres;for(i=1;i<=n;++i) s[i]=i;random_shuffle(s+1,s+n+1),res=Calc(),Gmax(ans,res);//随机初始序列
    			for(double tt=1e7;tt>1e-3;tt*=0.995)
    			{
    				W((x=rand()%n+1)==(y=rand()%n+1));swap(s[x],s[y]),nres=Calc(),Gmax(ans,nres);
    				(nres>res||exp((res-nres)/tt)>1.0*rand()/RAND_MAX)?res=nres:swap(s[x],s[y]);
    			}
    		}
    	public:
    		I void Solve() {srand(20030909);for(RI i=1;i<=SA_TIME;++i) Work();printf("%d",ans);}
    }S;
    int main()
    {
    	RI i,x,y;scanf("%d",&n);W(~scanf("%d%d",&x,&y)) f[x][y]=f[y][x]=1;//读入,建图
    	return S.Solve(),0;
    }
    
  • 相关阅读:
    SCCM 补丁更新 失误排错一例
    Oracle 远程连接 DB配置 连接命令
    反向代理服务器
    用JMF播放音频 例子
    HTML css兼容
    Java国际化
    JBPM 之介绍,使用
    Nginx内核优化引用
    Nginx 学习
    局域网访问VMware虚拟机中的Ubuntu
  • 原文地址:https://www.cnblogs.com/chenxiaoran666/p/Luogu4212.html
Copyright © 2011-2022 走看看