复习下树状数组

还是蛮有意思的一道题:

http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=501&page=show_problem&problem=4174

学到几点:

1、树状数组C[i]的构建,一则c[i]=s[i]-s[i-lowbit(i)];这是一直用的做法。如今学到一种新的,直接add(i,a[i]),(s[i]为a[1]到a[i]的和)

2、前缀和思想,树状数组的Sum本身就是基于前缀和的思想。本题把比某数小的数的个数,通过开大量空间+后缀数组,高效的统计出来比某数小的数的个数

3、事实上我认为通过这个题。能够做出来一种O(nlogn)的排序算法。当然不完好的地方就是仅仅能是整数了,可是应该能够用vector+map解决?

贴自己的代码先。,,由于后面的Lrj大牛的代码太简洁...

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <queue>
#include <functional> using namespace std; #define MAXN 20010
#define SIZE 100015 int a[MAXN],sma[SIZE],c[SIZE],s[SIZE],e[SIZE],tot[SIZE];
int n,mmax; int lowbit(int i)
{
return i & (-i);
} int sum(int i)
{
int ans=0;
for(;i>0;i-=lowbit(i))
ans+=c[i];
return ans;
} void add(int x, int d) {
while(x <= SIZE) {
c[x] += d; x += lowbit(x);
}
} void Init()
{
memset(c,0,sizeof(c));
memset(a,0,sizeof(a));
memset(sma,0,sizeof(sma));
memset(s,0,sizeof(s));
memset(e,0,sizeof(e));
memset(tot,0,sizeof(tot));
} int main()
{
//freopen("la4329.txt","r",stdin);
int t;
long long ans; scanf("%d",&t); while(t--)
{
mmax=0;
ans=0;
Init(); scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%d",&a[i]);
mmax=max(mmax,a[i]);
add(a[i],1);
//c[i]=sum(a[i]-1);
e[a[i]]=1;
sma[a[i]]=sum(a[i]-1); }
memset(c,0,sizeof(c));
for(int i=1;i<=mmax;i++)
{
s[i] =s[i-1]+e[i];
c[i]=s[i]-s[i-lowbit(i)];
tot[i]=sum(i-1);
}
///////////////////////
//for(int i=1;i<=n;i++)
//{
// printf("sma[a[%d]] = %d tot(%d) = %d\n",i,sma[a[i]],a[i],tot[a[i]]);
//}
///////////////////////
for(int i=1;i<=n;i++)
{
int tmp = tot[a[i]]-sma[a[i]];/*a[i]之后比a[i]小的个数*/
ans+=(long long )tmp*(i-1-sma[a[i]])+(long long)sma[a[i]]*(n-i-tmp);
} printf("%lld\n",ans);
} return 0;
}

标程

// LA4329 Ping pong
// Rujia Liu
#include<cstdio>
#include<vector>
using namespace std; //inline int lowbit(int x) { return x&(x^(x-1)); }
inline int lowbit(int x) { return x&-x; } struct FenwickTree {
int n;
vector<int> C; void resize(int n) { this->n = n; C.resize(n); }
void clear() { fill(C.begin(), C.end(), 0); } // ¼ÆËãA[1]+A[2]+...+A[x] (x<=n)
int sum(int x) {
int ret = 0;
while(x > 0) {
ret += C[x]; x -= lowbit(x);
}
return ret;
} // A[x] += d (1<=x<=n)
void add(int x, int d) {
while(x <= n) {
C[x] += d; x += lowbit(x);
}
}
}; const int maxn = 20000 + 5;
int n, a[maxn], c[maxn], d[maxn];
FenwickTree f; int main() {
freopen("la4329.txt","r",stdin);
int T;
scanf("%d", &T);
while(T--) {
scanf("%d", &n);
int maxa = 0;
for(int i = 1; i <= n; i++) { scanf("%d", &a[i]); maxa = max(maxa, a[i]); }
f.resize(maxa);
f.clear();
for(int i = 1; i <= n; i++) {
f.add(a[i], 1);
c[i] = f.sum(a[i]-1);
}
f.clear();
for(int i = n; i >= 1; i--) {
f.add(a[i], 1);
d[i] = f.sum(a[i]-1);
} long long ans = 0;
for(int i = 1; i <= n; i++)
ans += (long long)c[i]*(n-i-d[i]) + (long long)(i-c[i]-1)*d[i];
printf("%lld\n", ans);
}
return 0;
}

树状数组 LA 4329 亚洲赛北京赛区题的更多相关文章

  1. HDU 6278 - Just h-index - [莫队算法+树状数组+二分][2018JSCPC江苏省赛C题]

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6278 Time Limit: 6000/3000 MS (Java/Others) Memory Li ...

  2. POJ 2155 Matrix 【二维树状数组】(二维单点查询经典题)

    <题目链接> 题目大意: 给出一个初始值全为0的矩阵,对其进行两个操作. 1.给出一个子矩阵的左上角和右上角坐标,这两个坐标所代表的矩阵内0变成1,1变成0. 2.查询某个坐标的点的值. ...

  3. 二维树状数组+差分【p4514】上帝造题的七分钟

    Description "第一分钟,X说,要有矩阵,于是便有了一个里面写满了\(0\)的\(n\times m\)矩阵. 第二分钟,L说,要能修改,于是便有了将左上角为\((a,b)\),右 ...

  4. 树状数组+二分答案查询第k大的数 (团体程序设计天梯赛 L3-002. 堆栈)

    前提是数的范围较小 1 数据范围:O(n) 2 查第k大的数i:log(n)(树状数组查询小于等于i的数目)*log(n)(二分找到i) 3 添加:log(n) (树状数组) 4 删除:log(n) ...

  5. 【BZOJ-3881】Divljak AC自动机fail树 + 树链剖分+ 树状数组 + DFS序

    3881: [Coci2015]Divljak Time Limit: 20 Sec  Memory Limit: 768 MBSubmit: 508  Solved: 158[Submit][Sta ...

  6. poj 2155 Matrix---树状数组套树状数组

    二维树状数组模版,唯一困难,看题!!(其实是我英语渣) Matrix Time Limit: 3000MS Memory Limit: 65536K Total Submissions: 22098 ...

  7. poj2155 树状数组 Matrix

    Matrix Time Limit: 3000MS   Memory Limit: 65536K Total Submissions: 14826   Accepted: 5583 Descripti ...

  8. Why Did the Cow Cross the Road III(树状数组)

    Why Did the Cow Cross the Road III 时间限制: 1 Sec  内存限制: 128 MB提交: 65  解决: 28[提交][状态][讨论版] 题目描述 The lay ...

  9. [BZOJ4765]普通计算姬(分块+树状数组)

    4765: 普通计算姬 Time Limit: 30 Sec  Memory Limit: 256 MBSubmit: 1725  Solved: 376[Submit][Status][Discus ...

随机推荐

  1. C89:应用篇 文件管理器

    一.简介 用C语言做的一个文件管理器的轮子,因为经常开发中会用到跟数据流有关的,做完会放到Github上

  2. NPOI--------------.Net操作Excel初步使用(导出)

    背景 因公司项目需要添加数据导出功能故此添加,找了几种方式发现该方式具有 无需依赖本机安装office环境,使用灵活等优点故采用此方式. 安装 Nuget 直接安装NPOI即可 使用方式 1.根据需要 ...

  3. 洛谷——P1731 [NOI1999]生日蛋糕

    P1731 [NOI1999]生日蛋糕 搜索+剪枝 常见的剪枝: 若当前状态+后面所要搜索的最差的状态$>$或是$<$最后的状态,就返回 预处理最差的状态 #include<iost ...

  4. CSU——2161: 漫漫上学路 最短路

    Description 众所周知,CSU(California State)University) 的上课地点距离学生公寓很远,对于爱睡懒觉的小Z来说,每天去上课就成了一件非常头疼的事,如果有早课的话 ...

  5. CF508E Arthur and Brackets

    题目大意:给出n对括号,并给出每对括号距离的范围.问能否找到这样一个序列. 题解:好多人都用贪心.这么好的题为什么不搜一发呢? 注意:千万不要在dfs里面更新答案. 代码: #include<c ...

  6. oracle亲手安装过程

    适用于centos6 radhat6版本 1.检查依赖库: rpm -q binutils compat-libcap1 compat-libstdc++ compat-libstdc++.i686 ...

  7. lnmp -memcached使用

    系统需求: CentOS/RHEL/Fedora/Debian/Ubuntu/Raspbian/Deepin Server/Aliyun/Amazon/Mint Linux发行版 需要5GB以上硬盘剩 ...

  8. Python之面向对象多态

    Python之面向对象多态 多态与多态性: 多态: 多态是指一类事物有多种形态,一个抽象类有多个子类,因而多态的概念依赖于继承. 1.序列类型有多种形态:字符串.列表.元组. 2.动物有多种形态:Pe ...

  9. LeetCode(64) Minimum Path Sum

    题目 Total Accepted: 47928 Total Submissions: 148011 Difficulty: Medium Given a m x n grid filled with ...

  10. Automation 的 ReportFlow

    ReportFlow: // click the Grid icon and switch to grid page public void changeToGrid() // click the A ...