码迷,mamicode.com
首页 > 其他好文 > 详细

Segment题解

时间:2019-10-23 09:18:02      阅读:74      评论:0      收藏:0      [点我收藏+]

标签:模板   clu   inline   str   c++   printf   space   线段   包含   

Segment题解

对于初学李超树的我简直是噩梦,它比之前的模板题(上一篇博客)恶心在所有线段不再覆盖全区间。
我们要分情况讨论了:
对于被插入线段包含的区间,我们仍像之前一样操作;
部分包含的,像普通线段树一样分割插入线段的区间就行了,并不要修改。

if(p<=mid) update(l,mid,p,q,id,lc);
if(q>mid) update(mid+1,r,p,q,id,rc);

总代码:

#include<bits/stdc++.h>
#define re register
#define lc x<<1
#define rc x<<1|1
using namespace std;
const int N=1e5+6,M=4e4,mod1=39989,mod2=1e9;
int n,t1,t2,t3,t4,tag[M<<2],num=0,opt,last_ans=0;
struct xd{double s,p;}line[N];
inline int read(){
   int T=0,F=1; char ch=getchar();
   while(ch<'0'||ch>'9'){if(ch=='-') F=-1; ch=getchar();}
   while(ch>='0'&&ch<='9') T=(T<<3)+(T<<1)+(ch-48),ch=getchar();
   return F*T;
}
double f(int id,int x){return line[id].p*x+line[id].s;}
void update(int l,int r,int p,int q,int id,int x){
    int mid=l+r>>1;
    if(p<=l&&r<=q){
       if(l==r){if(f(id,l)>f(tag[x],l)) tag[x]=id; return;}
       if(line[tag[x]].p>line[id].p){
           if(f(tag[x],mid)<f(id,mid)) update(mid+1,r,mid+1,r,tag[x],rc),tag[x]=id;
           else update(l,mid,l,mid,id,lc);
       }
       else{
          if(f(tag[x],mid)<f(id,mid)) update(l,mid,l,mid,tag[x],lc),tag[x]=id;
          else update(mid+1,r,mid+1,r,id,rc);
       }
       return;
    }
    if(p<=mid) update(l,mid,p,q,id,lc);
    if(q>mid) update(mid+1,r,p,q,id,rc);
}
int query(int l,int r,int p,int x){
    if(l==r) return tag[x];
    int mid=l+r>>1,t; double ans=f(tag[x],p);
    if(p<=mid){t=query(l,mid,p,lc); return ans>f(t,p)?tag[x]:t;}
    t=query(mid+1,r,p,rc); return ans>f(t,p)?tag[x]:t;
}
int main(){
    n=read();
    for(int i=1;i<=n;++i){
        opt=read();
        if(!opt) t1=read(),t1=(t1+last_ans-1)%mod1+1,last_ans=query(1,M,t1,1),printf("%d\n",last_ans);
        else{
           t1=read(),t3=read(),t2=read(),t4=read(),t1=(t1+last_ans-1)%mod1+1,t2=(t2+last_ans-1)%mod1+1,t3=(t3+last_ans-1)%mod2+1,t4=(t4+last_ans-1)%mod2+1;
           if(t1>t2) swap(t1,t2),swap(t3,t4);
           ++num,line[num].p=(t1==t2)?0:(t4-t3)*1.00000000/(t2-t1),line[num].s=max(t4-t2*line[num].p,t3-t1*line[num].p),update(1,M,t1,t2,num,1);
        }
    }
    return 0;
}

Segment题解

标签:模板   clu   inline   str   c++   printf   space   线段   包含   

原文地址:https://www.cnblogs.com/ljk123-de-bo-ke/p/11723864.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!