Question D: Sunshine and rain (discretization + line segment tree/dynamic opening point)

Ideas:

Well, 1e9.. There is no dynamic opening board in the game, and the final mle is numb after more than 1 hour of handwriting adjustment. Changed the dynamic wording the next day, and then re. Crazy re. Just changed it out to re70 points.

Let's put the wording of discretization first. (It's really convenient.. Why can't I think about it in the game)

#include<iostream>
#include<vector>
#include<queue>
#include<cstring>
#include<cmath>
#include<map>
#include<set>
#include<cstdio>
#include<algorithm>
#define debug(a) cout<<#a<<"="<<a<<endl;
using namespace std;
const int maxn=4e5+1000;
typedef long long LL;
inline LL read(){LL x=0,f=1;char ch=getchar();  while (!isdigit(ch)){if (ch=='-') f=-1;ch=getchar();}while (isdigit(ch)){x=x*10+ch-48;ch=getchar();}
return x*f;}
struct Tree{
    LL l,r,val,tag;
}tree[maxn*4];
LL a[maxn*3];
LL tot=0;
struct Q{
    LL op,l,r,x;
}q[maxn];
void push_up(LL p){
    tree[p].val=max(tree[p*2].val,tree[p*2+1].val);
}
void addtag(LL p,LL d){
    tree[p].tag+=d;
    tree[p].val+=d;
}
void push_down(LL p){
    if(tree[p].tag!=0){
        addtag(p*2,tree[p].tag);
        addtag(p*2+1,tree[p].tag);
        tree[p].tag=0;
    }
}
void build(LL p,LL l,LL r){
    tree[p].l=l;tree[p].r=r;tree[p].val=1;tree[p].tag=0;
    if(l==r){return;}
    LL mid=(l+r)>>1;
    build(p*2,l,mid);
    build(p*2+1,mid+1,r);
    push_up(p);
}
void modify(LL p,LL l,LL r,LL d){
    if(l<=tree[p].l&&r>=tree[p].r){
        addtag(p,d);
        return;
    }
    push_down(p);
    LL mid=(tree[p].l+tree[p].r)>>1;
    if(l<=mid) modify(p*2,l,r,d);
    if(r>mid) modify(p*2+1,l,r,d);
    push_up(p);
}
LL query(LL p,LL l,LL r){
    if(l<=tree[p].l&&r>=tree[p].r){
        return tree[p].val;
    }
    push_down(p);
    LL mid=(tree[p].l+tree[p].r)>>1;
    LL ans=1;
    if(l<=mid) ans=max(ans,query(p*2,l,r));
    if(r>mid) ans=max(ans,query(p*2+1,l,r));
    return ans;
}
int main(void){
    cin.tie(0);std::ios::sync_with_stdio(false);
    LL n,m;cin>>n>>m;

    for(LL i=1;i<=m;i++){
        cin>>q[i].op;
        if(q[i].op==1){
            cin>>q[i].l>>q[i].r>>q[i].x;
        }
        else if(q[i].op==2){
            cin>>q[i].l>>q[i].r;
        }
        a[++tot]=q[i].l;
        a[++tot]=q[i].r;
    }
    sort(a+1,a+1+tot);
    LL siz=unique(a+1,a+1+tot)-a-1;

    build(1,1,siz);

    for(LL i=1;i<=m;i++){

        if(q[i].op==1){
            LL l=lower_bound(a+1,a+1+siz,q[i].l)-a;
            LL r=lower_bound(a+1,a+1+siz,q[i].r)-a;
            LL x=q[i].x;
            modify(1,l,r,x);
        }
        else if(q[i].op==2){
            LL l=lower_bound(a+1,a+1+siz,q[i].l)-a;
            LL r=lower_bound(a+1,a+1+siz,q[i].r)-a;
            cout<<query(1,l,r)<<"\n";
        }
    }
}

Dynamically open. re70 points

Open 28 times mle, 27 times re...It should be really stuck

#include<iostream>
#include<vector>
#include<queue>
#include<cstring>
#include<cmath>
#include<map>
#include<set>
#include<cstdio>
#include<algorithm>
#define debug(a) cout<<#a<<"="<<a<<endl;
using namespace std;
const int maxn=2e5+5;
typedef int LL;
inline LL read(){LL x=0,f=1;char ch=getchar();  while (!isdigit(ch)){if (ch=='-') f=-1;ch=getchar();}while (isdigit(ch)){x=x*10+ch-48;ch=getchar();}
return x*f;}
struct Tree{
   LL l,r,tag,val;
   LL lson=0,rson=0;
}tree[maxn*32];
LL tot=0;
LL newTree(LL now,LL last,LL l,LL r){
    tree[now].l=l;tree[now].r=r;
    //tree[now].tag=tree[last].tag;///继承父亲的tag
    tree[now].val=1;
    //tree[now].lson=tree[now].rson=0;
  ///  debug(now);
    return now;
}
void addtag(LL now,LL d){
	
    tree[now].tag+=d;
    tree[now].val+=d;
    //cout<<tree[now].l<<tree[now].r<<" "<<tree[now].tag<<"\n";
}
void push_down(LL now){
    if(tree[now].tag){
        LL l=tree[now].l;LL r=tree[now].r;
        LL mid=(l+r)>>1;

        if(!tree[now].lson) tree[now].lson=newTree(++tot,now,l,mid);
        addtag(tree[now].lson,tree[now].tag);
        if(!tree[now].rson) tree[now].rson=newTree(++tot,now,mid+1,r);
        addtag(tree[now].rson,tree[now].tag);
        tree[now].tag=0;
    }
}
void push_up(LL now){
    LL lmax=1;LL rmax=1;
    if(tree[now].lson) lmax=tree[ tree[now].lson].val;
    if(tree[now].rson) rmax=tree[ tree[now].rson].val;
    tree[now].val=max(lmax,rmax);
}
LL times=0;
void update(LL now,LL l,LL r,LL d){
     //cout<<tree[now].l<<" "<<tree[now].r<<"\n";
    //if(now==0) now=++tot;
    push_down(now);
     if(l<=tree[now].l&&r>=tree[now].r){
        addtag(now,d);
        return;
     }     
     LL mid=(tree[now].l+tree[now].r)>>1;
 //    times++;
 //    debug(mid);
  /*   if(times>=10){
        return;
     }*/
     //if(tree[now].l!=tree[now].r){

        if(l<=mid){
            if(!tree[now].lson) tree[now].lson=newTree(++tot,now,tree[now].l,mid);
            update(tree[now].lson,l,r,d);
        }
        if(r>mid){
            if(!tree[now].rson) tree[now].rson=newTree(++tot,now,mid+1,tree[now].r);
            update(tree[now].rson,l,r,d);
        }
     //}
     push_up(now);
}
LL query(LL now,LL l,LL r){
    //if( (!tree[now].l) && (!tree[now].r)  ) return tree[now].val;
    //cout<<tree[now].l<<" "<<tree[now].r<<" "<<tree[now].val<<"\n";
    if(now==0) return 0;
    push_down(now);
    if(l<=tree[now].l&&r>=tree[now].r){
        return tree[now].val;
    }
    LL mid=(tree[now].l+tree[now].r)>>1;
    LL ans=1;
    if(l<=mid) ans=max(ans,query(tree[now].lson,l,r));
    if(r>mid) ans=max(ans,query(tree[now].rson,l,r));
    return ans;
}
int main(void){
  ///  cin.tie(0);std::ios::sync_with_stdio(false);
    LL n,m;cin>>n>>m;
    tree[++tot].l=1;tree[tot].r=n;
    tree[tot].lson=tree[tot].rson=0;
    tree[tot].val=1;tree[tot].tag=0;///默认高度是1
    //cout<<"fuck"<<"\n";
    for(LL i=1;i<=m;i++){
        LL op;cin>>op;
        if(op==1){
            LL l,r,x;cin>>l>>r>>x;
            update(1,l,r,x);
        }
        else if(op==2){
            LL l,r;cin>>l>>r;
            cout<<query(1,l,r)<<"\n";
        }
    }
}

 

Guess you like

Origin blog.csdn.net/zstuyyyyccccbbbb/article/details/114835439