hdu 4000 - Fruit Ninja(树状数组)
题意:
给定一个1到n的排列,输出三元组(x,y,z) (满足条件x<z<y)的个数。
思路:
建立树状数组,对于每个位置都求出前面比a[i]小的数字的个数L,好后面比a[i]大的数字的个数R, 则有该位置作为开始的的满足条件的三元组包含在R(R-1)个中,当然其中参杂着(x,y,z)(x<y<z),这样的三元组可以有L*R得到,二者之差便是答案,
代码如下:
#include <cstdio> #include <cstring> #include <cstdlib> #include <cmath> #include <queue> #include <stack> #include <list> #include <vector> #include <map> #include <algorithm> #define LL long long #define LLU unsigned long long #define INF 0x7fffffff #define MOD 100000007 using namespace std; #define lowbit(x) x&-x #define M 100005 int c[M]; LL sum(int x) { LL ret = 0; while(x>0) { ret += c[x]; x -= lowbit(x); } return ret; } void add(int x, int n) { while(x<=n) { c[x] += 1; x += lowbit(x); } } int main () { int t, n, x, k = 0; scanf("%d",&t); while(t--) { scanf("%d", &n); LL ans = 0; memset(c,0,sizeof(c)); for(int i = 1; i <= n; ++i) { scanf("%d",&x); add(x, n); LL l = sum(x-1); LL r = n - i - x + l + 1; ans -= l*r; if(r>=2) ans += r*(r-1)/2; } printf("Case #%d: %I64d\n",++k, ans%MOD); } return 0; }