BZOJ 4411: [Usaco2016 Feb]Load balancing 线段树+二分

code: 

#include <bits/stdc++.h>     
#define N 100060   
#define M 1000000 
#define lson x<<1 
#define rson x<<1|1 
#define ll long long 
#define setIO(s) freopen(s".in","r",stdin) 
using namespace std;                  
int n,num[N*10],ans=N,X0,X1;    
struct node 
{
    int x0,x1; 
}t[N*10*4];   
struct Point
{
    int x,y;   
    friend bool operator<(Point a,Point b) { return a.y<b.y; }   
}a[N];     
void pushup(int x) 
{   
    t[x].x0=t[lson].x0+t[rson].x0; 
    t[x].x1=t[lson].x1+t[rson].x1;    
}   
void build(int x,int l,int r) 
{
    if(l==r) 
    {
        t[x].x0=num[l];     
        t[x].x1=0;     
        return;  
    }
    int mid=(l+r)>>1;  
    build(lson,l,mid); 
    build(rson,mid+1,r);  
    pushup(x); 
}
void update(int x,int l,int r,int p) 
{
    if(l==r) 
    {
        t[x].x0--,t[x].x1++; 
        return; 
    } 
    int mid=(l+r)>>1;  
    if(p<=mid)  update(lson,l,mid,p); 
    else update(rson,mid+1,r,p);        
    pushup(x); 
}
int ask(int x,int l,int r,int x0,int x1) 
{
    if(l==r) return l;   
    int mid=(l+r)>>1;   
    int sum0=x0+t[lson].x0,sum1=x1+t[lson].x1;    
    if(max(sum0,sum1)>=max(t[1].x0-sum0,t[1].x1-sum1))  
    {
        return ask(lson,l,mid,x0,x1);   
    } 
    else
    {
        return ask(rson,mid+1,r,sum0,sum1);  
    }
}   
void qsum(int x,int l,int r,int L,int R) 
{
    if(L>R) return;   
    if(l>=L&&r<=R) 
    {
        X0+=t[x].x0; 
        X1+=t[x].x1; 
        return;  
    } 
    int mid=(l+r)>>1;  
    if(L<=mid)  qsum(lson,l,mid,L,R); 
    if(R>mid)   qsum(rson,mid+1,r,L,R);   
}
int main() 
{ 
    // setIO("input"); 
    int i,j; 
    scanf("%d",&n); 
    for(i=1;i<=n;++i) scanf("%d%d",&a[i].x,&a[i].y), num[a[i].x]++;  
    sort(a+1,a+1+n); 
    build(1,1,M); 
    for(i=1,j;i<=n;i=j) 
    {
        j=i; 
        while(j<=n&&a[j].y==a[i].y)  update(1,1,M,a[j].x),++j;    
        int pos=ask(1,1,M,0,0);   
        X0=0,X1=0,qsum(1,1,M,1,pos);    
        ans=min(ans,max(X0,X1));       
        X0=0,X1=0,qsum(1,1,M,1,pos-1);     
        ans=min(ans,max(t[1].x0-X0,t[1].x1-X1));   
    }   
    printf("%d
",ans);  
    return 0;   
}

  

原文地址:https://www.cnblogs.com/guangheli/p/12058558.html