hdu 5147 Sequence II【树状数组/线段树】
Sequence II
Time Limit: 5000/2500 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Problem Description
Long long ago, there is a sequence A with length n. All numbers in this sequence is no smaller than 1 and no bigger than n, and all numbers are different in this sequence.
Please calculate how many quad (a,b,c,d) satisfy:
1≤a<b<c<d≤n
Aa<Ab
Ac<Ad
Input
The first line contains a single integer T, indicating the number of test cases.
Each test case begins with a line contains an integer n.
The next line follows n integers A1,A2,…,An.
[Technical Specification]
1 <= T <= 100
1 <= n <= 50000
1 <= Ai <= n
Output
For each case output one line contains a integer,the number of quad.
Sample Input
1
5
1 3 2 4 5
Sample Output
4
题意:有一个长度为n的数列A,数列中的每个数都在1到n之间,且数列中不存在两个相同的数。
请统计有多少四元组(a,b,c,d)满足:
1≤a<b<c<d≤n
Aa<Ab
Ac<Ad
思路:
这是道树状数组/线段树基础题。我们平时更新线段树或树状数组时都是按输入顺序从1到n更新,而还有某些题是需要你以他给定的数值大小的范围建树,把输入的数放到相对应的位置上(一般是对应位置标记),然后进行相关操作,本题即使如此。
我们讲一下树状数组的做法,线段树同理,只不过写起来麻烦一点。这道题我们按道理来说是需要每次确定四个数的,但明显会t,所以我们之多枚举一个数(这道题确定b或者确定c都可以,我们这里讲一下确定b的做法)。既然确定了b,我们就得想办法确定出b前面比它小的数和它后面满足Ac<Ad的个数,所以这里我们引入前缀和,后缀和来维护。对于刚开始而言,树状数组的所有1至n的点都是还没有被标记的,每当输入一个数时,比如输入5,我们就将它放在5的那个位置上(即更新树状数组把5的位置标记为1),这样我们去查询5前面有多少个数被标记过了,说明这些数是先被输入的,位置在这个数前面,这样子我们就维护出了一个在b前面比Ab小的数的个数的数组。
那接下来我们要如何确定b后面的那些呢?这里我们可以稍微算一下,对于输入的第i个数a[i],我们已经算出了前面比它小的数pre[i],那么对于i+1位置的数来说,比它大的数就是n-a[i]-(i-1-pre[i]),n-a[i]代表i这个位置后面还有多少个数,i-1-pre[i]代表i前面有多少个数比a[i]大,这样就可以算出i后面有多少个数比a[i]大。把这个后缀和维护出来,枚举b的位置把每个点的可能种类数加起来便可,注意答案可能爆int。
代码:
#include "stdio.h"
#include "string.h"
const int N=1e5+; int t,n,a[N],c[N];
long long ans,pre[N],last[N]; int lowbit(int x)
{
return x&(-x);
} int update(int x)
{
for(int i=x;i<=n;i+=lowbit(i))
c[i]++; ///标记该点
} int getsum(int x)
{
int sum=;
for(int i=x;i>=;i-=lowbit(i))
sum+=c[i]; ///算i位置前比a[i]小的数的个数
return sum;
} int main()
{
scanf("%d",&t);
while(t--)
{
ans=;
memset(c,,sizeof(c));
memset(pre,,sizeof(pre));
memset(last,,sizeof(last));
scanf("%d",&n);
for(int i=;i<=n;i++)
{
scanf("%d",&a[i]);
pre[i]=getsum(a[i]); ///pre[i]代表比a[i]小的数的个数
update(a[i]);
}
for(int i=n;i>=;i--)
last[i]=n-a[i]-(i--pre[i]); ///算出i位置后面比a[i]大的数的个数
for(int i=n;i>=;i--)
last[i]+=last[i+]; ///累加即使i点后面满足Ac<Ad的这个数
for(int i=1;i<=n;i++)
ans+=(pre[i]*last[i+1]); ///枚举b点位置累加答案
printf("%lld\n",ans);
}
return ;
}
hdu 5147 Sequence II【树状数组/线段树】的更多相关文章
- 树状数组 && 线段树应用 -- 求逆序数
参考:算法学习(二)——树状数组求逆序数 .线段树或树状数组求逆序数(附例题) 应用树状数组 || 线段树求逆序数是一种很巧妙的技巧,这个技巧的关键在于如何把原来单纯的求区间和操作转换为 求小于等于a ...
- hdu1394(枚举/树状数组/线段树单点更新&区间求和)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1394 题意:给出一个循环数组,求其逆序对最少为多少: 思路:对于逆序对: 交换两个相邻数,逆序数 +1 ...
- 洛谷P2414 阿狸的打字机 [NOI2011] AC自动机+树状数组/线段树
正解:AC自动机+树状数组/线段树 解题报告: 传送门! 这道题,首先想到暴力思路还是不难的,首先看到y有那么多个,菜鸡如我还不怎么会可持久化之类的,那就直接排个序什么的然后按顺序做就好,这样听说有7 ...
- hdu 1166:敌兵布阵(树状数组 / 线段树,入门练习题)
敌兵布阵 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submis ...
- hdu 3966 Aragorn's Story(树链剖分+树状数组/线段树)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3966 题意: 给出一棵树,并给定各个点权的值,然后有3种操作: I C1 C2 K: 把C1与C2的路 ...
- hdu 1166 敌兵布阵——(区间和)树状数组/线段树
pid=1166">here:http://acm.hdu.edu.cn/showproblem.php?pid=1166 Input 第一行一个整数T.表示有T组数据. 每组数据第一 ...
- HDU 1166 敌兵布阵 树状数组||线段树
http://acm.hdu.edu.cn/showproblem.php?pid=1166 题目大意: 给定n个数的区间N<=50000,还有Q个询问(Q<=40000)求区间和. 每个 ...
- HDU 3303 Harmony Forever 前缀和+树状数组||线段树
Problem Description We believe that every inhabitant of this universe eventually will find a way to ...
- Holedox Eating HDU - 4302 2012多校C 二分查找+树状数组/线段树优化
题意 一个长度$n<=1e5$的数轴,$m<=1e5$个操作 有两种一些操作 $0$ $x$ 在$x$放一个食物 $1$ 一个虫子去吃最近的食物,如果有两个食物一样近,不转变方向的去吃 ...
随机推荐
- 关于Android 的内存泄露及分析(转)
一. Android的内存机制Android的程序由Java语言编写,所以Android的内存管理与Java的内存管理相似.程序员通过new为对象分配内存,所有对象在java堆内分配空间:然而对象的释 ...
- 《新标准C++程序设计》4.2-4.3(C++学习笔记13)
一.重载赋值运算符“=” 赋值运算符“=”要求左右两个操作数的类型是匹配的,或至少是兼容的.有时候希望赋值运算符两边的类型可以不匹配,比如,把一个int类型变量赋值给一个Complex对象,或把一个 ...
- Django(二) 模板:基本使用、模板语法、模板继承
一.模板的使用实战 接:https://blog.csdn.net/u010132177/article/details/103788677 参考:https://docs.djangoproject ...
- 【转帖】影响超 10 亿设备,博通和 Cypress 芯片曝惊天漏洞,苹果、华为、三星等中招
影响超 10 亿设备,博通和 Cypress 芯片曝惊天漏洞,苹果.华为.三星等中招 https://www.infoq.cn/article/lpNEQGrxZL22gHDPBE2z 26 ...
- 51nod 1055:最长等差数列
1055 最长等差数列 基准时间限制:2 秒 空间限制:262144 KB 分值: 80 难度:5级算法题 收藏 取消关注 N个不同的正整数,找出由这些数组成的最长的等差数列. 例如:1 3 5 ...
- Gerrit部署成功后project下不显示clone地址
gerrit部署成功后使用admin账号登录,在project All-projects下不显示clone地址,新建仓库也不显示. 原因是:默认安装没有安装插件download-commands 安装 ...
- 【java】【反射】反射实现判断发生了修改操作,判断两个对象是否发生属性值的变更,判断两个List集合内对象的属性值是否发生变更
java的反射实现: 判断发生了修改操作,判断两个对象是否发生属性值的变更,判断两个List集合内对象的属性值是否发生变更 今日份代码: package com.sxd.streamTest; imp ...
- 065-PHP函数中声明全局变量
<?php function test(){ //定义函数 global $a; //声明全局变量 $a=7; echo "函数内: ".$a . "<br& ...
- 4. 异步多级缓存架构+nginx数据本地化渲染
- ELK 教程
自从ELK首次推出以来,下载量达到了数百万次,是世界上最流行的日志管理平台.相比之下,Splunk - 该领域的历史领先者 - 宣布的客户总数才15000人. 章节 ELK 介绍 ELK 安装Elas ...