#include <cstdio>
#include <iostream>
#include <algorithm>
using namespace std;
#define MAX_N 100000+10
typedef long long ll;
ll bit0[MAX_N],bit1[MAX_N];
int N,X[MAX_N],Y[MAX_N];
vector <int> line[MAX_N];
bool visted[MAX_N];
ll sum(ll *b, int i){
int s = 0;
while(i > 0){
s += b[i];
i -= (i & -i);
}
return s;
}
ll sum(ll *bit, int from, int to){
return sum(bit, to-1) - sum(bit, from - 1);
}
void add(ll *b, int i, int v){
while(i <= MAX_N){
b[i] += v;
i += (i & -i);
}
}
ll sum(int from, int to){
return sum(to) - sum(from);
}
void add(int from,int to,ll x){
add(bit0, from, -x*(from-1));
add(bit1, from , x);
add(bit0, to , x * to);
add(bit1, to , -x);
}
int compress(int *p){
vector<int> ps(N);
for(int i = 0;i < N; i++){
ps[i] = p[i];
}
sort(ps.begin(), ps.end());
ps.erase(unique(ps.begin(), ps.end()), ps.end());
for(int i = 0;i < N; i++){
p[i] = 1 + distance(ps.begin(), lower_bound(ps.begin(), ps.end(), p[i]));
}
return ps.size();
}
int main(){
scanf("%d", &N);
for(int i = 0;i < N; i++)
scanf("%d%d", X+i, Y+i);
int w = compress(X);
int h = compress(Y);
for(int i = 0;i < N; i++){
line[Y[i]].push_back(X[i]);
}
ll result = N;
for(int y = 0;y < h; y++){
vector <int >& xs = line[y];
sort(xs.begin(), xs.end());
for(vector<int>::iterator i = xs.begin(); i != xs.end(); i++){
int x = *i;
ll s = sum(x - 1, x);
if(visited[x]){
result += s;
}else {
visted[x] = true;
}
add(bit0, x, -s);
if(i + 1 != xs.end()){
if (x + 1 < *(i + 1) - 1) // 下一个黑子
{
add(x + 1, *(i + 1) - 1, 1); // 遇到了空白
}
else if (x + 1 == *(i + 1) - 1)
{
add(bit0, x + 1, 1); // 遇到了空白,此时等同于add(x + 1, x + 1, 1);
}
}
}
}
printf("%lld\n" result);
return 0;
}
poj 3109 Inner Vertices 树状数组+离散化
最新推荐文章于 2020-05-27 17:10:39 发布