ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

BZOJ 4399: 魔法少女LJJ 线段树合并 + 对数

2019-07-31 14:01:19  阅读:219  来源: 互联网

标签:4399 LJJ return int mid re p1 ls BZOJ


Code: 

#include <cstdio>
#include <algorithm> 
#include <cmath> 
using namespace std; 
#define ls lson[x]
#define rs rson[x]  
#define setIO(s) freopen(s".in","r",stdin),freopen(s".out","w",stdout) 
const int maxn=500000;  
const int N=1000000000;  
namespace IO {  
    char *p1,*p2,buf[100000];
    #define nc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++)
    int rd() {
        int x=0; 
        char c=nc(); 
        while(c<48) c=nc(); 
        while(c>47) x=(((x<<2)+x)<<1)+(c^48),c=nc(); 
        return x;
    }
};   
struct UFS { 
    int p[maxn];         
    void init() {
        for(int i=0;i<maxn;++i) p[i]=i; 
    }  
    int find(int x) {
        return p[x]==x?x:p[x]=find(p[x]); 
    }
}tr; 
int cnt;  
int rt[maxn],lson[maxn*10],rson[maxn*10],num[maxn*10];      
double de[maxn*10];
int newnode() {
    return ++cnt;  
} 
void pushup(int x) {
    num[x]=num[ls]+num[rs]; 
    de[x]=de[ls]+de[rs];   
}
void update(int &x,int l,int r,int p,int v) {
    if(!x)x=newnode();                    
    if(l==r) {
        num[x]+=v, de[x]+=(double)v*(double)(log(p));      
        return;   
    } 
    int mid=(l+r)>>1;       
    if(p<=mid) update(ls,l,mid,p,v); 
    else update(rs,mid+1,r,p,v); 
    pushup(x); 
}
int merge(int x,int y) {
    if(!x||!y) return x+y;   
    num[x]+=num[y]; 
    de[x]+=de[y];    
    lson[x]=merge(lson[x],lson[y]);  
    rson[x]=merge(rson[x],rson[y]);    
    return x; 
}    
int less(int &x,int l,int r,int k) { 
    if(!x||l>=k) return 0;   
    int re=0; 
    if(r<k) {
        re=num[x],x=0; 
        return re;  
    }        
    if(l==r) return 0;   
    int mid=(l+r)>>1;     
    re+=less(ls,l,mid,k); 
    re+=less(rs,mid+1,r,k);       
    pushup(x); 
    return re;     
}
int bigger(int &x,int l,int r,int k) {
    if(!x||r<=k) return 0;  
    int re=0; 
    if(l>k) {
        re=num[x],x=0; 
        return re; 
    } 
    if(l==r) return 0; 
    int mid=(l+r)>>1; 
    re+=bigger(ls,l,mid,k); 
    re+=bigger(rs,mid+1,r,k); 
    pushup(x); 
    return re;   
}
int kth(int x,int l,int r,int k) {     
    if(l==r) return l;        
    int mid=(l+r)>>1;   
    if(k>num[ls]) return kth(rs,mid+1,r,k-num[ls]); 
    else return kth(ls,l,mid,k);        
}
int main() {   
    using namespace IO;  
    int m,cc=0;  
    m=rd(); 
    tr.init();    
    for(int cas=1;cas<=m;++cas) { 
        int op=rd(); 
        if(op==1) {
            int x=rd();  
            ++cc;  
            update(rt[cc],1,N,x,1);    
        }
        if(op==2) {
            int x,y,a,b; 
            x=rd(),y=rd(); 
            a=tr.find(x),b=tr.find(y);        
            if(a!=b) {
                rt[b]=merge(rt[a],rt[b]);            
                tr.p[a]=b;   
            }
        }       
        if(op==3) {
            int a,x,c=0; 
            a=rd(),x=rd(); 
            a=tr.find(a);   
            c=less(rt[a],1,N,x);         
            update(rt[a],1,N,x,c); 
        }
        if(op==4) {
            int a,x,c=0; 
            a=rd(),x=rd(); 
            a=tr.find(a); 
            c=bigger(rt[a],1,N,x);   
            update(rt[a],1,N,x,c);       
        }
        if(op==5) {
            int a,k;  
            a=rd(),k=rd(); 
            a=tr.find(a);              
            printf("%d\n",kth(rt[a],1,N,k));   
        }
        if(op==6) {          
            int a,b; 
            a=rd(),b=rd(); 
            a=tr.find(a),b=tr.find(b);      
            if(de[rt[a]]>de[rt[b]]) printf("1\n"); 
            else printf("0\n"); 
        }
        if(op==7) { 
            int a; 
            a=rd(); 
            a=tr.find(a); 
            printf("%d\n",num[rt[a]]);  
        } 
    }    
    return 0; 
}

  

标签:4399,LJJ,return,int,mid,re,p1,ls,BZOJ
来源: https://www.cnblogs.com/guangheli/p/11275836.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有