HDU 5517 Triple(去重+线段树|二维树状数组)



1000线
线线


代码:

#include <map>
#include <set>
#include <stack>
#include <queue>
#include <cmath>
#include <string>
#include <vector>
#include <cstdio>
#include <cctype>
#include <cstring>
#include <sstream>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#pragma comment(linker,"/STACK:102400000,102400000")

using namespace std;
#define   MAX           200005
#define   MAXN          1000005
#define   maxnode       15
#define   sigma_size    30
#define   lson          l,m,rt<<1
#define   rson          m+1,r,rt<<1|1
#define   lrt           rt<<1
#define   rrt           rt<<1|1
#define   middle        int m=(r+l)>>1
#define   LL            long long
#define   ull           unsigned long long
#define   mem(x,v)      memset(x,v,sizeof(x))
#define   lowbit(x)     (x&-x)
#define   pii           pair<int,int>
#define   bits(a)       __builtin_popcount(a)
#define   mk            make_pair
#define   limit         10000

//const int    prime = 999983;
const int    INF   = 0x3f3f3f3f;
const LL     INFF  = 0x3f3f;
const double pi    = acos(-1.0);
const double inf   = 1e18;
const double eps   = 1e-8;
const int    mod   = 1e9+7;
const ull    mx    = 133333331;

/*****************************************************/
inline void RI(int &x) {
      char c;
      while((c=getchar())<'0' || c>'9');
      x=c-'0';
      while((c=getchar())>='0' && c<='9') x=(x<<3)+(x<<1)+c-'0';
 }
/*****************************************************/

int pre[MAX];
int num[MAX];
map<pair<pii,int>,int> ma;
struct Node{
    int a,b,c;
    LL num;
    bool operator < (const Node &e)const{
        if(a==e.a){
            if(b==e.b) return c>e.c;
            return b>e.b;
        }
        return a>e.a; 
    }
}p[MAX];

int maxv[MAX<<2];

void pushup(int rt){
    maxv[rt]=max(maxv[lrt],maxv[rrt]);
}

void build(int l,int r,int rt){
    if(l==r){
        maxv[rt]=0;
        return;
    }
    middle;
    build(lson);
    build(rson);
    pushup(rt);
}

void update(int l,int r,int rt,int pos,int d){
    if(l==r){
        maxv[rt]=max(maxv[rt],d);
        return;
    }
    middle;
    if(pos<=m) update(lson,pos,d);
    else update(rson,pos,d);
    pushup(rt);
}

int query(int l,int r,int rt,int L,int R){
    if(L<=l&&r<=R) return maxv[rt];
    middle;
    int ans=0;
    if(L<=m) ans=max(ans,query(lson,L,R));
    if(R>m) ans=max(ans,query(rson,L,R));
    return ans;
}
int main(){
    //freopen("in.out","r",stdin);
    int t,kase=0;
    cin>>t;
    while(t--){
        int n,m;
        cin>>n>>m;
        mem(pre,0);
        mem(num,0);
        ma.clear();
        for(int i=0;i<n;i++){
            int a,b;
            scanf("%d%d",&a,&b);
            if(pre[b]<a){
                pre[b]=a;
                num[b]=1;
            }
            else if(pre[b]==a) num[b]++;
        }
        int tot=0;
        for(int i=0;i<m;i++){
            int a,b,c;
            scanf("%d%d%d",&a,&b,&c);
            if(pre[c]) p[tot++]=(Node){pre[c],a,b,num[c]};
        }
        sort(p,p+tot);
        int len=0;
        p[len++]=p[0];
        for(int i=1;i<tot;i++){
            if(p[i].a==p[len-1].a&&p[i].b==p[len-1].b&&p[i].c==p[len-1].c) p[len-1].num+=p[i].num;
            else p[len++]=p[i];
        }
        tot=len;
        build(1,1000,1);
        LL ans=0;
        for(int i=0;i<tot;i++){
            int ret=query(1,1000,1,p[i].b,1000);
            if(ret<p[i].c) ans+=p[i].num;
            update(1,1000,1,p[i].b,p[i].c);     
        }
        kase++;
        printf("Case #%d: ",kase);
        cout<<ans<<endl;
    }
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值