首页 > 其他 > 详细

Luogu P2073 送花

时间:2019-11-14 10:49:54      阅读:77      评论:0      收藏:0      [点我收藏+]

题目传送门

操作2和操作3反着写是什么鬼?反人类


权值线段树的模板题

然而AC后才发现,可以用\(\tt{set}\)水过……

权值线段树类似于用线段树来实现平衡树的一些操作,代码实现还是比较方便的

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define ls p<<1
#define rs p<<1|1
#define mid ((l+r)>>1)
using namespace std;
struct zzz{
    int w,c;
}tree[1000000<<2];
inline void up(int p){ //合并线段树的信息
    tree[p].w=tree[ls].w+tree[rs].w;
    tree[p].c=0;
    if(tree[ls].w) tree[p].c+=tree[ls].c;
    if(tree[rs].w) tree[p].c+=tree[rs].c;
}
void build(int l,int r,int p){  //初始化线段树
    if(l==r){
        tree[p].c=l; return ;
    }
    build(l,mid,ls); build(mid+1,r,rs);
}
void add(int l,int r,int p,int k,int f){  //添加一朵美丽值为f,价格为k的花
    if(l==r){
        if(tree[p].w) return ;
        tree[p].w=f; return ;
    }
    else if(k<=mid) add(l,mid,ls,k,f);
    else add(mid+1,r,rs,k,f);
    up(p);
}
void del1(int l,int r,int p){  //去掉最便宜的花
    if(l==r){
        tree[p].w=0; return ;
    }
    if(tree[ls].w) del1(l,mid,ls);
    else del1(mid+1,r,rs);
    up(p);
}
void del2(int l,int r,int p){  //去掉最贵的花
    if(l==r){
        tree[p].w=0; return ;
    }
    if(tree[rs].w) del2(mid+1,r,rs);
    else del2(l,mid,ls);
    up(p);
}
int read(){
    int k=0,f=1; char c=getchar();
    for(;c<'0'||c>'9';c=getchar())
      if(c=='-') f=-1;
    for(;c>='0'&&c<='9';c=getchar())
      k=k*10+c-48;
    return k*f;
}
int main(){
    build(1,1000001,1);
    int k=read();
    while(k!=-1){
        if(k==1){
            int w=read(),c=read();
            add(1,1000001,1,c,w);
        }
        if(k==3) del1(1,1000001,1);
        if(k==2) del2(1,1000001,1);
        k=read();
    }
    cout<<tree[1].w<<" "<<tree[1].c;
    return 0;
}

Luogu P2073 送花

原文:https://www.cnblogs.com/morslin/p/11854897.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!