zoukankan      html  css  js  c++  java
  • 【以前的空间】BZOJ2733[HNOI2012]永无乡

    启发式合并?!

    似乎当时写并查集的时候就有看到过类似于把小并查集并到大并查集上的说法,原来这就是启发式……

    具体做法就是把小树里面的一个个拿出来,然后加到大树里面去(裸的不敢相信)

    const
    
      maxn=300000;
    
      number=32323231;
    
    var
    
      left,right,size,value,hash,key,fa,num,root:array[0..maxn]of longint;
    
      tot:longint;
    
    
    
    procedure swap(var x,y:longint);
    
    var
    
      i:longint;
    
    begin
    
      i:=x;
    
      x:=y;
    
      y:=i;
    
    end;
    
    
    
    procedure lt(var x:longint);
    
    var
    
      k:longint;
    
    begin
    
      k:=right[x];
    
      right[x]:=left[k];
    
      left[k]:=x;
    
      size[k]:=size[x];
    
      size[x]:=size[left[x]]+size[right[x]]+1;
    
      x:=k;
    
    end;
    
    
    
    procedure rt(var x:longint);
    
    var
    
      k:longint;
    
    begin
    
      k:=left[x];
    
      left[x]:=right[k];
    
      right[k]:=x;
    
      size[k]:=size[x];
    
      size[x]:=size[left[x]]+size[right[x]]+1;
    
      x:=k;
    
    end;
    
    
    
    procedure insert(var x:longint;y:longint);
    
    begin
    
      if x=0 then begin
    
        inc(tot);
    
        x:=tot;
    
        value[x]:=num[y];
    
        hash[x]:=y;
    
        key[x]:=random(number);
    
        left[x]:=0;
    
        right[x]:=0;
    
        size[x]:=1;
    
        exit;
    
      end;
    
      inc(size[x]);
    
      if value[x]<num[y] then begin
    
        insert(right[x],y);
    
        if key[right[x]]<key[x] then lt(x);
    
      end
    
      else begin
    
        insert(left[x],y);
    
        if key[left[x]]<key[x] then rt(x);
    
      end;
    
    end;
    
    
    
    procedure dfs(var x:longint;y:longint);
    
    begin
    
      if y=0 then exit;
    
      insert(x,hash[y]);
    
      dfs(x,left[y]);
    
      dfs(x,right[y]);
    
    end;
    
    
    
    function getfa(x:longint):longint;
    
    begin
    
      if fa[x]=x then exit(x);
    
      fa[x]:=getfa(fa[x]);
    
      exit(fa[x]);
    
    end;
    
    
    
    procedure link(x,y:longint);
    
    begin
    
      x:=getfa(x);
    
      y:=getfa(y);
    
      if x=y then exit;
    
      if size[root[x]]<size[root[y]] then swap(x,y);
    
      dfs(root[x],root[y]);
    
      fa[y]:=x;
    
    end;
    
    
    
    function find(x,y:longint):longint;
    
    begin
    
      if x=0 then exit(-1);
    
      if size[left[x]]=y-1 then exit(hash[x]);
    
      if size[left[x]]>y-1 then exit(find(left[x],y))
    
        else exit(find(right[x],y-size[left[x]]-1));
    
    end;
    
    
    
    procedure into;
    
    var
    
      i,x,y,n,m:longint;
    
    begin
    
      readln(n,m);
    
      randomize;
    
      for i:=1 to n do begin
    
        read(num[i]);
    
        fa[i]:=i;
    
        insert(root[i],i);
    
      end;
    
      for i:=1 to m do begin
    
        readln(x,y);
    
        link(x,y);
    
      end;
    
    end;
    
    
    
    procedure work;
    
    var
    
      n,x,y,i:longint;
    
      ch:char;
    
    begin
    
      readln(n);
    
      for i:=1 to n do begin
    
        readln(ch,x,y);
    
        case ch of
    
          'B':link(x,y);
    
          'Q':writeln(find(root[getfa(x)],y));
    
        end;
    
      end;
    
    end;
    
    
    
    begin
    
      into;
    
      work;
    
    end.
    View Code
  • 相关阅读:
    excel读取表,并将结果保存为键值对的字典列表;
    [置顶] MQ选型对比RabbitMQ RocketMQ ActiveMQ Kafka
    ActiveMQ持久化消息的三种方式
    getConstructor、getDeclaredConstructor区别
    JavaEE 保存文件获取绝对路径getResource("")和servletContext.getRealPath("/")
    Java中getResourceAsStream的用法
    Java 输出流中的flush方法
    Java之关闭流
    Java中的字节流、缓冲流
    java原生序列化和Kryo序列化性能比较
  • 原文地址:https://www.cnblogs.com/Macaulish/p/6492138.html
Copyright © 2011-2022 走看看