zoukankan      html  css  js  c++  java
  • codevs 4543 treap 模板

    type rec=record
     lc,rc,v,rnd,size,w,fa:longint;
          end;
    
    var
     n,root,tot,ans,opt,x,i,po:longint;
     tr:array[0..100000] of rec;
    
     procedure rotl(po:longint);
     var
      y:longint;
       begin
         y:=tr[po].rc;
         tr[po].rc:=tr[y].lc;
         if tr[y].lc>0 then tr[tr[y].lc].fa:=po;
         tr[y].fa:=tr[po].fa;
         if tr[po].fa=0 then root:=y else
           if po=tr[tr[po].fa].lc then
             tr[tr[po].fa].lc:=y else tr[tr[po].fa].rc:=y;
         tr[y].lc:=po;
         tr[po].fa:=y;
         tr[y].size:=tr[po].size;
         tr[po].size:=tr[tr[po].lc].size+tr[tr[po].rc].size+tr[po].w;
       end;
    
     procedure rotr(po:longint);
     var
      y:longint;
       begin
         y:=tr[po].lc;
         tr[po].lc:=tr[y].rc;
         if tr[y].rc>0 then tr[tr[y].rc].fa:=po;
         tr[y].fa:=tr[po].fa;
         if tr[po].fa=0 then root:=y else
           if po=tr[tr[po].fa].lc then
             tr[tr[po].fa].lc:=y else tr[tr[po].fa].rc:=y;
         tr[y].rc:=po;
         tr[po].fa:=y;
         tr[y].size:=tr[po].size;
         tr[po].size:=tr[tr[po].lc].size+tr[tr[po].rc].size+tr[po].w;
       end;
    
     procedure ins(x,po:longint);
       begin
         inc(tr[po].size);
         if x=tr[po].v then
           begin
            inc(tr[po].w);
            exit;
           end;
    
         if x<tr[po].v then
           begin
             if tr[po].lc=0 then
               begin
                 inc(tot);
                 tr[tot].fa:=po;
                 tr[tot].v:=x;
                 tr[tot].size:=1;
                 tr[tot].w:=1;
                 tr[tot].rnd:=random(10000)+1;
                 tr[po].lc:=tot;
                 if tr[tot].rnd<tr[po].rnd then rotr(po);
               end else
                begin
                 ins(x,tr[po].lc);
                 if tr[tr[po].lc].rnd<tr[po].rnd then rotr(po);
                end;
           end;
    
           if x>tr[po].v then
            begin
              if tr[po].rc=0 then
               begin
                 inc(tot);
                 tr[tot].fa:=po;
                 tr[tot].v:=x;
                 tr[tot].size:=1;
                 tr[tot].w:=1;
                 tr[tot].rnd:=random(10000)+1;
                 tr[po].rc:=tot;
                 if tr[tot].rnd<tr[po].rnd then rotl(po);
               end else
                begin
                 ins(x,tr[po].rc);
                 if tr[tr[po].rc].rnd<tr[po].rnd then rotl(po);
                end;
            end;
       end;
    
      function find(x,po:longint):longint;
        begin
          dec(tr[po].size);
          if x<tr[po].v then exit(find(x,tr[po].lc));
          if x>tr[po].v then exit(find(x,tr[po].rc));
          if x=tr[po].v then exit(po);
        end;
    
      procedure del(po:longint);
        begin
          while(tr[po].lc>0) or (tr[po].rc>0) do
            begin
              if tr[po].lc=0 then
                begin
                  rotl(po);
                  tr[tr[po].fa].size:=tr[tr[tr[po].fa].rc].size+tr[tr[po].lc].size+tr[tr[po].rc].size+tr[tr[po].fa].w;
                  continue;
                end;
    
              if tr[po].rc=0 then
                begin
                  rotr(po);
                   tr[tr[po].fa].size:=tr[tr[tr[po].fa].lc].size+tr[tr[po].lc].size+tr[tr[po].rc].size+tr[tr[po].fa].w;
                  continue;
                end;
    
              if tr[tr[po].lc].rnd>tr[tr[po].rc].rnd then
               begin
                rotl(po);
                tr[tr[po].fa].size:=tr[tr[tr[po].fa].rc].size+tr[tr[po].lc].size+tr[tr[po].rc].size+tr[tr[po].fa].w;
               end
                else
               begin
                rotr(po);
                tr[tr[po].fa].size:=tr[tr[tr[po].fa].lc].size+tr[tr[po].lc].size+tr[tr[po].rc].size+tr[tr[po].fa].w;
               end;
            end;
    
           if tr[tr[po].fa].lc=po then
             begin
               tr[tr[po].fa].lc:=0;
               tr[tr[po].fa].size:=tr[tr[tr[po].fa].rc].size+tr[tr[po].fa].w;
             end
           if tr[tr[po].fa].rc=po then
             begin
               tr[tr[po].fa].rc:=0;
               tr[tr[po].fa].size:=tr[tr[tr[po].fa].lc].size+tr[tr[po].fa].w;
             end;
    
             tr[po].size:=0;tr[po].w:=0;
    
           end;
    
      procedure num(x,po:longint);
       begin
         if x<=tr[tr[po].lc].size then
           begin
             num(x,tr[po].lc);
             exit;
           end;
    
         if x>tr[tr[po].lc].size+tr[po].w then
           begin
             num(x-tr[tr[po].lc].size-tr[po].w,tr[po].rc);
             exit;
           end;
    
         writeln(tr[po].v);
       end;
    
      procedure rank(x,po:longint);
        begin
          if x<tr[po].v then
            begin
              rank(x,tr[po].lc);
              exit;
            end;
    
          if x>tr[po].v then
            begin
              ans:=ans+tr[tr[po].lc].size+tr[po].w;
              rank(x,tr[po].rc);
              exit;
            end;
    
            ans:=ans+tr[tr[po].lc].size+1;
        end;
    
     procedure pre(x,po:longint);
       begin
         if po=0 then exit;
         if (tr[po].v<x) then
           begin
             ans:=tr[po].v;
             pre(x,tr[po].rc);
           end else pre(x,tr[po].lc);
       end;
    
     procedure suc(x,po:longint);
       begin
         if po=0 then exit;
         if (tr[po].v>x) then
           begin
             ans:=tr[po].v;suc(x,tr[po].lc);
           end else  suc(x,tr[po].rc);
       end;
    
      begin
    
        randomize;
        read(n);
    
    
        for i:=1 to n do
          begin
            read(opt,x);
            if opt=1 then
              begin
                if tr[root].w=0 then
                  begin
                    inc(tot);
                    tr[tot].v:=x;tr[tot].size:=1;tr[tot].w:=1;
                    tr[tot].rnd:=random(10000)+1;
                    root:=tot;
                  end else ins(x,root);
              end;
            if opt=2 then begin po:=find(x,root);if tr[po].w>1 then begin dec(tr[po].w);continue;end;del(po); end;
            if opt=3 then begin ans:=0;rank(x,root); writeln(ans);end;
            if opt=4 then num(x,root);
            if opt=5 then begin pre(x,root); writeln(ans); end;
            if opt=6 then begin suc(x,root); writeln(ans); end;
          end;
    
    
      end.

    ------------------------------------------------------

    非旋treap

    CODECHEF LTIME16 CHEFC

    #include <cstdio>
    #include <algorithm>
    #define LL long long 
    using namespace std;
    
      int a[200001],T,n,root,q;
    
      struct treenode{
          int lc,rc,lv,rv,v,ans,size;
      }tr[200001];
    
      void update(int po){
          if (!tr[po].lc) tr[po].lv=tr[po].v;else tr[po].lv=tr[tr[po].lc].lv;
          if (!tr[po].rc) tr[po].rv=tr[po].v;else tr[po].rv=tr[tr[po].rc].rv;
          
          tr[po].ans=tr[tr[po].lc].ans+tr[tr[po].rc].ans;
          if (tr[po].lc) tr[po].ans+=tr[po].v!=tr[tr[po].lc].rv;
          if (tr[po].rc) tr[po].ans+=tr[po].v!=tr[tr[po].rc].lv;
          
          tr[po].size=tr[tr[po].lc].size+tr[tr[po].rc].size+1;
      }
    
      int build(int l,int r){
          int mid=(l+r)>>1;
          tr[mid].v=a[mid];tr[mid].size=tr[mid].ans=0;tr[mid].lc=tr[mid].rc=0;
          if (l==r){
            tr[mid].lv=tr[mid].rv=tr[mid].v;tr[mid].size=1;
            return(mid);    
        }
          
          if (l!=mid) tr[mid].lc=build(l,mid-1);
          if (r!=mid) tr[mid].rc=build(mid+1,r);
          update(mid);
          return(mid);
      }
    
      void split(int po,int &root1,int &root2,int k){
          if (tr[tr[po].lc].size==k){
            root1=tr[po].lc;root2=po;
            tr[po].lc=0;
            update(po);
            return;
        }
        if (tr[tr[po].lc].size==k-1){
          root1=po;root2=tr[po].rc;
          tr[po].rc=0;
          update(po);
          return;
        }
        
        if (k<=tr[tr[po].lc].size){
          split(tr[po].lc,root1,root2,k);
          tr[po].lc=root2;
          update(po);
          root2=po;    
        }else{
          split(tr[po].rc,root1,root2,k-tr[tr[po].lc].size-1);
          tr[po].rc=root1;
          update(po);
          root1=po;
        }
      }
    
      int merge(int po1,int po2){
          if (po1==0||po2==0) return(po1|po2);
          
          if ((LL)rand()*tr[po1].size>(LL)rand()*tr[po2].size){
            tr[po1].rc=merge(tr[po1].rc,po2);
          update(po1);
          return(po1);    
        }else{
          tr[po2].lc=merge(po1,tr[po2].lc);
          update(po2);
          return(po2);
        }
      }
    
      void dfs_show(int po){
          if (tr[po].lc) dfs_show(tr[po].lc);
          printf("%d ",tr[po].v);
          if (tr[po].rc) dfs_show(tr[po].rc);
      }
    
      int main(){      
          scanf("%d",&T);
          while (T--){
            scanf("%d",&n);
          for (int i=1;i<=n;i++) scanf("%d",&a[i]);
          root=build(1,n);
          
          scanf("%d",&q);
          for (int i=1;i<=q;i++){
              int opt,l,r;
              scanf("%d%d%d",&opt,&l,&r);
              int root1,root2,root3;
              split(root,root1,root2,l-1);
            
              split(root2,root2,root3,r-l+1);
              
              if (opt==2){
                root1=merge(root1,root3);
              root=merge(root2,root1);
            }else{
              printf("%d
    ",tr[root2].ans+1);
              root2=merge(root2,root3);
              root=merge(root1,root2);    
            }
          }
        }
      }
  • 相关阅读:
    use imagination
    tar
    简单抓取安居客房产数据,并保存到Oracle数据库
    svn的安装(整合apache、ldap)包括错误解决post commit FS processing had error
    SVN安装中遇到的问题
    Linux环境源码编译安装SVN
    [转]SVN安装问题The Apache Portable Runtime (APR) library cannot be found
    深入浅出数据分析-脑图
    Python3.5在Windows 7下连接ORACLE数据库
    Python3.5之TuShare
  • 原文地址:https://www.cnblogs.com/zhujiangning/p/5212731.html
Copyright © 2011-2022 走看看