• BZOJ2599: [IOI2011]Race


    裸的点分治

    自从前两天狂敲了一个广搜点分治之后 敲个点分治如鱼得水啊

    总觉得自己的写法会被奇怪数据卡到O(n2)

    幸好IOI数据比较仁慈…

    调试小结:

      1. now、po不分

      2. dis、deep不分

    P.S. IOI的数据格式…不想讲了

      1 /**************************************************************
      2     Problem: 2599
      3     User: zhuohan123
      4     Language: C++
      5     Result: Accepted
      6     Time:30648 ms
      7     Memory:43504 kb
      8 ****************************************************************/
      9  
     10 #include <iostream>
     11 #include <cstdio>
     12 #include <algorithm>
     13 //#define ONLINE_JUDGE
     14 using namespace std;
     15 inline int imin(int a,int b){return a<b?a:b;}
     16 int n,k;
     17 struct point{int f,head,deep,dis,size,wt;bool havevis;}p[210000];
     18 struct edge{int next,to,c;}g[510000];int gnum;
     19 void addedge(int from,int to,int c)
     20 {
     21     g[++gnum].to=to;g[gnum].c=c;g[gnum].next=p[from].head;p[from].head=gnum;
     22 }
     23 int q1[1100000],l1=1,r1=0;
     24 int bfsx[110000],bfsnum;
     25 void BFS(int po)
     26 {
     27     p[po].f=0;p[po].deep=0;p[po].dis=0;
     28     l1=1;r1=0;bfsnum=0;
     29     q1[++r1]=po;
     30     while(l1<=r1)
     31     {
     32         int now=q1[l1++];
     33         bfsx[++bfsnum]=now;
     34         p[now].size=1;
     35         for(int i=p[now].head;i;i=g[i].next)
     36             if(g[i].to!=p[now].f&&!p[g[i].to].havevis)
     37             {
     38                 p[g[i].to].f=now;
     39                 p[g[i].to].deep=p[now].deep+1;
     40                 p[g[i].to].dis=p[now].dis+g[i].c;
     41                 q1[++r1]=g[i].to;
     42             }
     43     }
     44     for(int i=bfsnum;i>1;i--)p[p[bfsx[i]].f].size+=p[bfsx[i]].size;
     45 }
     46 int bestroot(int po)
     47 {
     48     int halfsize=p[po].size/2;
     49     while(true)
     50     {
     51         int bpo=0,bsize=-1;
     52         for(int i=p[po].head;i;i=g[i].next)
     53             if(!p[g[i].to].havevis&&bsize<p[g[i].to].size)bsize=p[bpo=g[i].to].size;
     54         if(bsize<=halfsize)return po;
     55         p[po].size-=p[bpo].size;
     56         p[bpo].size+=p[po].size;
     57         po=bpo;
     58     }
     59 }
     60 int q3[1100000],l3=1,r3=0;
     61 void settree(int po)
     62 {
     63     l3=1;r3=0;
     64     q3[++r3]=po;
     65     while(l3<=r3)
     66     {
     67         int now=q3[l3++];
     68         p[now].wt=po;
     69         for(int i=p[now].head;i;i=g[i].next)
     70             if(g[i].to!=p[now].f&&!p[g[i].to].havevis)
     71             q3[++r3]=g[i].to;
     72     }
     73 }
     74 struct isort
     75 {
     76     int wt,dis,deep;
     77     isort(){wt=dis=deep=0;}
     78     isort(int Wt,int Dis,int Deep){wt=Wt;dis=Dis;deep=Deep;}
     79     friend bool operator<(isort a,isort b)
     80     {
     81         if(a.dis<b.dis)return true;
     82         else if(a.dis==b.dis&&a.wt<a.wt)return true;
     83         else if(a.dis==b.dis&&a.wt==a.wt&&a.deep<b.deep)return true;
     84         return false;
     85     }
     86 }s[1100000];int snum;
     87 int q4[1100000],l4=1,r4=0;
     88 void BFS2(int po)
     89 {
     90     l4=1;r4=0;
     91     q4[++r4]=po;
     92     while(l4<=r4)
     93     {
     94         int now=q4[l4++];
     95         s[++snum]=isort(p[now].wt,p[now].dis,p[now].deep);
     96         for(int i=p[now].head;i;i=g[i].next)
     97             if(g[i].to!=p[now].f&&!p[g[i].to].havevis)
     98             q4[++r4]=g[i].to;
     99     }
    100 }
    101 int q2[1100000],l2=1,r2=0;
    102 int ans=2147483647;
    103 void idivide()
    104 {
    105     l2=1;r2=0;
    106     q2[++r2]=1;
    107     while(l2<=r2)
    108     {
    109         int now=q2[l2++];
    110         BFS(now);
    111         now=bestroot(now);
    112         BFS(now);
    113         p[now].havevis=true;
    114         for(int i=p[now].head;i;i=g[i].next)
    115             if(!p[g[i].to].havevis)settree(g[i].to);
    116         /*cout<<"------------------------------------------"<<endl;
    117         cout<<now<<endl;
    118         for(int i=1;i<=n;i++)cout<<i<<" f="<<p[i].f<<" deep="<<p[i].deep<<" dis="
    119         <<p[i].dis<<" size="<<p[i].size<<" wt="<<p[i].wt<<" havevis="<<p[i].havevis<<endl;
    120         cout<<"------------------------------------------"<<endl;*/
    121         snum=0;
    122         BFS2(now);
    123         sort(s+1,s+snum+1);
    124         int r=snum;
    125         for(int l=1;l<=snum;l++)
    126         {
    127             //if(s[l].dis==s[l-1].dis&&s[l].wt==s[l-1].wt)continue ;
    128             if(s[l].dis==k)
    129             {
    130                 ans=imin(ans,s[l].deep);
    131                 continue;
    132             }
    133             if(s[l].dis>k)break ;
    134             while(r&&(s[l].dis+s[r].dis>k))r--;
    135             if(r<=0)break ;
    136             if(s[l].dis+s[r].dis<k)continue ;
    137             for(int tempr=r;s[l].dis+s[tempr].dis==k;tempr--)
    138                 if(s[tempr].wt!=s[l].wt)
    139                     ans=imin(ans,s[l].deep+s[tempr].deep);
    140         }
    141         for(int i=p[now].head;i;i=g[i].next)
    142             if(!p[g[i].to].havevis)q2[++r2]=g[i].to;
    143     }
    144 }
    145 int main(int argc, char *argv[])
    146 {
    147     #ifndef ONLINE_JUDGE
    148         freopen("1.in","r",stdin);
    149         freopen("1.out","w",stdout);
    150     #endif
    151     scanf("%d%d",&n,&k);
    152     for(int i=1;i<n;i++)
    153     {
    154         int from,to,c;scanf("%d%d%d",&from,&to,&c);
    155         from++;to++;
    156         addedge(from,to,c);addedge(to,from,c);
    157     }
    158     p[0].deep=-1;
    159     idivide();
    160     if(ans==2147483647)ans=-1;
    161     //IOI丧心病狂数据
    162     #ifdef CENA
    163         int expect;scanf("%d",&expect);
    164         if(expect==ans)printf("Correct.
    ");
    165         else printf("My:%d Std:%d",ans,expect);
    166     #else
    167         printf("%d
    ",ans);
    168     #endif
    169     return 0;
    170 }

     还有一句老话:

      简单数据结构 永远不要用 STL!!!

  • 相关阅读:
    python模块添加
    Python 的列表排序
    python中文处理问题
    排序算法堆排序
    搜索二分搜索
    排序算法(随机)快速排序(递归)
    排序算法计数排序
    OO设计原则总结
    异常控制以及进程调度
    ubuntu12.04 alternate win7 双系统安装
  • 原文地址:https://www.cnblogs.com/zhuohan123/p/3231215.html
Copyright © 2020-2023  润新知