标签:
按顺序给出N个数字,求出所有的逆序对个数(逆序对指数字 Ai > Aj且 i < j)
题目链接:hiho_1141
数据规模为 100000,必须使用O(nlogn)的算法来进行求解。下标i从0到N-1,依次求出数字Ai,在A[0, i-1]中比Ai大的数字个数K,将所有的K进行加和即可得到结果。
这种动态的排序+统计,使用treap。
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<string>
#include<set>
#include<map>
#include<vector>
#include<queue>
#include<stack>
#include<unordered_map>
#include<unordered_set>
#include<algorithm>
using namespace std;
struct Node{
int val;
int priority;
int count;
int sum;
Node* childs[2];
Node(int v = 0) :val(v){
priority = rand();
childs[0] = childs[1] = NULL;
count = sum = 1;
}
void Update(){
sum = count;
if (childs[0])
sum += childs[0]->sum;
if (childs[1])
sum += childs[1]->sum;
}
};
struct Treap{
Node* root;
Treap(){
root = NULL;
}
void Rotate(Node*& node, bool dir){
Node* ch = node->childs[dir];
node->childs[dir] = ch->childs[!dir];
ch->childs[!dir] = node;
node->Update();
node = ch;
}
void Insert(Node*& node, int val){
if (!node){
node = new Node(val);
return;
}
if (node->val == val){
node->count++;
node->sum++;
return;
}
else{
bool dir = node->val < val;
Insert(node->childs[dir], val);
if (node->childs[dir]->priority > node->priority){
Rotate(node, dir);
}
node->Update();
}
}
int Search(Node* node, int val){
if (!node)
return 0;
if (node->val == val){
if (node->childs[1])
return node->childs[1]->sum;
else
return 0;
}
else if (node->val > val){
return Search(node->childs[0], val) + (node->childs[1]? node->childs[1]->sum + node->count : node->count);
}
else
return Search(node->childs[1], val);
}
};
int main(){
Treap treap;
int N;
scanf("%d", &N);
long long int count = 0;
int val;
for (int i = 0; i < N; i++){
scanf("%d", &val);
count += (treap.Search(treap.root, val));
treap.Insert(treap.root, val);
}
printf("%lld\n", count);
return 0;
}
标签:
原文地址:http://www.cnblogs.com/gtarcoder/p/5689957.html