传送门

废话:读错题了,写了半天结果发现写了一道假题。

题意:
三种操作:
操作①:在时间戳为T的多重集合中加入一个数字x。
操作②:在时间戳为T的多重集合中加入一个数字x。
操作③:询问在时间戳为T的多重集合中包好多少个数字x。

解题思路:
基础的二维偏序:对于操作时间 q1 和 q2,时间戳 t1 和 t2 ,数字 x 。 q1<q2 并且 t1<t2  操作②和操作①的数量差。
第一查询时间直接按照输入的来,可以降掉一维,剩下的一维按照时间戳升序,用分治解决。答案直接拿map记录数量就可以了。
如果让你求小于等于x的数量的个数,第三维我们就要用树状数组来维护信息。

代码:

///#include<bits/stdc++.h>
///#include<unordered_map>
///#include<unordered_set>
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<string>
#include<cmath>
#include<queue>
#include<bitset>
#include<set>
#include<stack>
#include<map>
#include<list>
#include<new>
#include<vector>
 
#define MT(a, b) memset(a,b,sizeof(a))
#define lowbit(x) (x&(-x))
using namespace std;
typedef long long ll;
const double pai = acos(-1.0);
const double E = 2.718281828459;
const ll mod = 20180623;
const double esp = 1e-6;
const int INF = 0x3f3f3f3f;
const int maxn = 1e5 + 5;
 
int n, cnt;
struct node {
    int op, t, x;
    int index;
} q[maxn], temp[maxn];
int ans[maxn];
 
bool cmp(node a, node b) {
    if(a.t == b.t) {
        if(a.x == b.x)
            return a.op < b.op;
        return a.x < b.x;
    }
    return a.t < b.t;
}
 
void cdq(int l, int r) {
    if (l == r)    return;
    int mid = (l + r) >> 1;
    cdq(l, mid), cdq(mid + 1, r);
    int ql = l, qr = mid + 1;
    map<int,int>num;
    for (int i = l; i <= r; i++) {
        if ((ql <= mid && cmp(q[ql], q[qr])) || qr > r) {
            if (q[ql].op == 1)
                num[q[ql].x]++;
            else if (q[ql].op == 2)
                num[q[ql].x]--;
            temp[i] = q[ql++];
        } else {
            if (q[qr].op == 3)
                ans[q[qr].index] +=num[q[qr].x];
            temp[i] = q[qr++];
        }
    }
    for (int i = l; i <= r; i++)
        q[i] = temp[i];
}
 
int main() {
    scanf("%d", &n);
    for (int i = 1; i <= n; i++) {
        scanf("%d %d %d", &q[i].op, &q[i].t, &q[i].x);
        if (q[i].op == 3)
            q[i].index = ++cnt;
    }
    cdq(1, n);
    for (int i = 1; i <= cnt; i++)
        printf("%d\n", ans[i]);
    return 0;
}