hdu 5147 Sequence II【树状数组/线段树】
Sequence II ? Problem Description 1≤a<b<c<d≤n [Technical Specification] Output Sample Input Sample Output 题意:有一个长度为n的数列A,数列中的每个数都在1到n之间,且数列中不存在两个相同的数。 1≤a<b<c<d≤n
代码: 1 #include "stdio.h"
2 #include "string.h"
3 const int N=1e5+5; 4
5 int t,n,a[N],c[N]; 6 long long ans,pre[N],last[N]; 7
8 int lowbit(int x) 9 { 10 return x&(-x); 11 } 12
13 int update(int x) 14 { 15 for(int i=x;i<=n;i+=lowbit(i)) 16 c[i]++; ///标记该点
17 } 18
19 int getsum(int x) 20 { 21 int sum=0; 22 for(int i=x;i>=1;i-=lowbit(i)) 23 sum+=c[i]; ///算i位置前比a[i]小的数的个数
24 return sum; 25 } 26
27 int main() 28 { 29 scanf("%d",&t); 30 while(t--) 31 { 32 ans=0; 33 memset(c,0,sizeof(c)); 34 memset(pre,sizeof(pre)); 35 memset(last,sizeof(last)); 36 scanf("%d",&n); 37 for(int i=1;i<=n;i++) 38 { 39 scanf("%d",&a[i]); 40 pre[i]=getsum(a[i]); ///pre[i]代表比a[i]小的数的个数
41 update(a[i]); 42 } 43 for(int i=n;i>=1;i--) 44 last[i]=n-a[i]-(i-1-pre[i]); ///算出i位置后面比a[i]大的数的个数
45 for(int i=n;i>=1;i--) 46 last[i]+=last[i+1]; ///累加即使i点后面满足Ac<Ad的这个数 47 for(int i=1;i<=n;i++) 48 ans+=(pre[i]*last[i+1]); ///枚举b点位置累加答案
49 printf("%lldn",ans); 50 } 51 return 0; 52 }
(编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |