码迷,mamicode.com
首页 > 编程语言 > 详细

三元逆序对 求i<j<k && a[i]>a[j]>a[k] 的对数 树状数组Codeforces 61E Enemy is weak

时间:2015-08-25 19:45:05      阅读:600      评论:0      收藏:0      [点我收藏+]

标签:

http://codeforces.com/problemset/problem/61/E

E. Enemy is weak
time limit per test
5 seconds
memory limit per test
256 megabytes
input
standard input
output
standard output

The Romans have attacked again. This time they are much more than the Persians but Shapur is ready to defeat them. He says: "A lion is never afraid of a hundred sheep".

Nevertheless Shapur has to find weaknesses in the Roman army to defeat them. So he gives the army a weakness number.

In Shapur‘s opinion the weakness of an army is equal to the number of triplets i,?j,?k such that i?<?j?<?k and ai?>?aj?>?ak where ax is the power of man standing at position x. The Roman army has one special trait — powers of all the people in it are distinct.

Help Shapur find out how weak the Romans are.

Input

The first line of input contains a single number n (3?≤?n?≤?106) — the number of men in Roman army. Next line contains n different positive integers ai (1?≤?i?≤?n,?1?≤?ai?≤?109) — powers of men in the Roman army.

Output

A single integer number, the weakness of the Roman army.

Please, do not use %lld specificator to read or write 64-bit integers in C++. It is preffered to use cout (also you may use %I64d).

Sample test(s)
input
3
3 2 1
output
1
input
3
2 3 1
output
0
input
4
10 8 3 1
output
4
input
4
1 5 4 3
output
1

题意是求 i<j<k && a[i]>a[j]>a[k] 的对数

如果只有2元组那就是求逆序数的做法

三元组的话就用一个树状数组x表示 数字i前面有多少个比自己大的个数

然后每次给这个y数组求和,再把x中>a[i]的个数存入y中即可

即使是4元也可以求了

#include <algorithm>
#include <cctype>
#include <cassert>
#include <cstdio>
#include <cstring>
#include <climits>
#include <vector>
#include<iostream>
using namespace std;
#define ll long long
inline void rd(int &ret)
{
	char c;
	do { c = getchar();
	} while(c < '0' || c > '9');
	ret = c - '0';
	while((c=getchar()) >= '0' && c <= '9')
		ret = ret * 10 + ( c - '0' );
}
#define N 1000005
#define eps 1e-8
#define inf 1000000


ll n;
struct node{
	ll c[N];
	inline ll lowbit(ll x){return x&-x;}
	void init(){memset(c, 0, sizeof c);}
	ll sum(ll x){
		ll ans = 0;
		while(x<=n+10)
			ans += c[x], x+=lowbit(x);
		return ans;
	}
	void change(ll x, ll y){
		while(x)
			c[x] +=y, x-=lowbit(x);
	}
}x, y;
int haifei[1000000], panting[1000000];
int main()
{
	ll i, j;
	while(cin>>n)
	{
		ll ans = 0;
		for(i = 0; i < n; i++)rd(haifei[i]), panting[i] = haifei[i];
		x.init(); y.init();
		sort(haifei, haifei+n);
		for(i = 0; i < n; i++)
		{
			ll b = (lower_bound(haifei, haifei+n, panting[i]) - haifei) +1;
			
			ll siz = y.sum(b);
			ans += siz;
			y.change(b, x.sum(b));
			x.change(b, 1);
		}
		cout<<ans<<endl;
	}
	return 0;
}


版权声明:本文为博主原创文章,未经博主允许不得转载。

三元逆序对 求i<j<k && a[i]>a[j]>a[k] 的对数 树状数组Codeforces 61E Enemy is weak

标签:

原文地址:http://blog.csdn.net/acm_10000h/article/details/47980083

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!