zoukankan      html  css  js  c++  java
  • 【WC2018】即时战略

    动态淀粉质即可

    #include "rts.h"
    #include<algorithm>
    #include<unordered_map>
    #include<cstdlib>
    #include<ctime>
    #include<map>
    const int maxn = 300300;
    int per[maxn],vis[maxn];
    typedef long long ll;
    std::map<int,int> ans[maxn];
    int N;
    inline int get(int x,int y){
        return explore(x,y);
    }
    namespace list{
        const int LEFT=1,RIGHT=0;
        inline void solve(int to,int&l,int&r,int type=LEFT){
            if(l==to||r==to)return ;
            if(type == LEFT){
                int p=get(l,to);
                if(vis[p])solve(to,l,r,RIGHT);
                else vis[p]=1,solve(to,l=p,r,type);
            }else{
                int p=get(r,to);
                vis[p]=1,solve(to,l,r=p,type);
            }
        }
    }
    namespace wwj{
        int n;
        const double alpha=0.6;
        struct sol_tree{
            int size,rt;
            std::map<int,sol_tree*> son;
            inline sol_tree(int p){size=1,rt=p;}
            inline ~ sol_tree(){son.clear();}
        };
        struct T{int to,nxt;}way[maxn<<1];
        int h[maxn],num;
        inline void adde(int x,int y){
            way[++num]={y,h[x]},h[x]=num;
            way[++num]={x,h[y]},h[y]=num;
        }
        inline void up(int&x,int y){if(x<y)x=y;}
        sol_tree ** rebd;
        int vis[maxn];
        namespace dfz{
            int vis[maxn],size[maxn];
            inline void init(){for(int i=1;i<=n;++i)vis[i]=1;}
            inline void getsz(int x){
                vis[x]=size[x]=1;
                for(int i=h[x];i;i=way[i].nxt)
                    if(!vis[way[i].to])getsz(way[i].to),size[x]+=size[way[i].to];
                vis[x]=0;
            }
            int rt,v;
            inline void getrt(int x,int al){
                vis[x]=1;
                int ms=0;
                for(int i=h[x];i;i=way[i].nxt)
                    if(!vis[way[i].to])getrt(way[i].to,al),up(ms,size[way[i].to]);
                if(std::max(al-size[x],ms)<v)v=std::max(al-size[x],ms),rt=x;
                vis[x]=0;
            }
            inline int getroot(int x){getsz(x),v=1e9,getrt(x,size[x]);return rt;}
            inline sol_tree* sol(int x){
                x=getroot(x),vis[x]=1;
                sol_tree * ret = new sol_tree(x);
                for(int i=h[x];i;i=way[i].nxt)
                    if(!vis[way[i].to]){
                        sol_tree * tmp=ret->son[way[i].to]=sol(way[i].to);
                        ret->size+=tmp->size;
                    }
                return ret;
            }
            inline void dfscls(sol_tree * rt){
                vis[rt->rt] = 0;
                for(std::pair<int,sol_tree*>i:rt->son)
                    dfscls(i.second);
                delete rt;
            }
        }
        int cnt,sumsz;
        inline void rebuild(sol_tree ** rebd){
            ++cnt;
            sol_tree* & rt = * rebd;
            int R = rt -> rt;sumsz+=rt->size;
            dfz::dfscls(rt);
            rt=dfz::sol(R);
        }
        inline int ins(sol_tree*&rt,int to){
            int p = get(rt -> rt,to);
            if(!vis[p]){
                sol_tree*&tmp=rt -> son[p] = new sol_tree(p);
                adde(rt -> rt,p),vis[p]=1;
                int res=0;
                if(p!=to)rt->size+=res=ins(tmp,to);
                if(rt -> size * alpha + 1 < tmp -> size)
                    rebd =&rt;
                return res+1;
            }else{
                sol_tree*&tmp=rt->son[p];
                int res=0;
                rt->size+=res=ins(tmp,to);
                if(rt -> size * alpha + 1 < tmp -> size)
                    rebd =&rt;
                return res;
            }
        }
        inline void solve(){
            srand(time(0));
            for(int i=1;i<=n;++i)per[i]=i;
            for(int i=1;i<=2;++i)std::random_shuffle(per+1,per+n+1);
            dfz::init();
            vis[1]=1;
            sol_tree * rt = new sol_tree(1);
            int cnt=n-1;
            while(cnt){
                int i=rand()%n+1;
                if(!vis[per[i]]){
                    rebd=0;
                    cnt-=ins(rt,per[i]);
                    if(rebd)rebuild(rebd);
                }
            }
        }
    }
    void play(int n, int T, int dataType){
        N=wwj::n=n;
        if(dataType == 3){
            srand(time(0));
            for(int i=1;i<=n;++i)per[i]=i;
            for(int i=1;i<=10;++i)std::random_shuffle(per+1,per+n+1);
            vis[1]=1;
            for(int i=1,l=1,r=1;i<=n;++i)if(!vis[per[i]])
                list::solve(per[i],l,r);
        }else{
            wwj::solve();
        }
    }
  • 相关阅读:
    css 实现div内显示两行或三行,超出部分用省略号显示
    vue组件中的样式属性:scoped,解决在父组件中无法修改子组件样式问题
    HBuilder打包app(vue项目)
    vue动态路由传值以及get传值及编程式导航
    vue路由vue-router的安装和使用
    vue组件传值之父传子
    vue生命周期钩子函数
    vue定义组件
    vue定义自定义事件方法、事件传值及事件对象
    vue中操作Dom节点的方法
  • 原文地址:https://www.cnblogs.com/skip1978/p/10342923.html
Copyright © 2011-2022 走看看