【算法笔记】树状数组/Binary Indexed Tree/Fenwick Tree

本文介绍了树状数组(Binary Indexed Tree),一种在O(log N)时间内支持区间求和与元素更新的数据结构。通过离散化和树状数组原理,实现高效逆序对计算及区间更新技巧。对比线段树,树状数组在实现和速度上有明显优势。

前言

树状数组,即树形存储的数组,又称Binary Indexed TreeFenwick Tree
抛开它树形的存储结构,这种神奇的数据结构的应用看起来与「 树」没什么关系:

有一个序列 A = ( A 1 , A 2 , … , A N ) A=(A_1,A_2,\dots,A_N) A=(A1,A2,,AN),在不超过 O ( log ⁡ N ) \mathcal O(\log N) O(logN)的时间复杂度内完成下列操作:
→   \to~   [ L , R ] [L,R] [L,R]区间内所有数之和。
→   \to~  指定一个元素 A x A_x Ax,将其加上 k k k

如果想要使求和操作尽可能快,很容易想到前缀和,这样求和操作只要 O ( 1 ) \mathcal O(1) O(1)的时间,但更新操作的时间复杂度就升至 O ( N ) \mathcal O(N) O(N),无法满足题目要求;反之,若直接暴力维护 A A A中所有元素的值,则虽然更新操作只需要 O ( 1 ) \mathcal O(1) O(1),但求和操作的时间又变成了 O ( N ) \mathcal O(N) O(N),还是满足不了要求。那有没有一种算法,综合了两种方式的优势,达到题目时间要求呢?

肯定有,那就是今天说的——树状数组。

基本算法

洛谷 P3374【模板】树状数组 1
同“前言”中的部分, 1 ≤ n , m ≤ 1 0 5 1\le n,m\le 10^5 1n,m105,其中 m m m为操作总次数。

由于 n , m ≤ 1 0 5 n,m\le 10^5 n,m105,所以 O ( n m ) \mathcal O(nm) O(nm)的暴力解法肯定行不通,需要使用 O ( M log ⁡ N ) \mathcal O(M\log N) O(MlogN)的树状数组。其存储结构大致上是这样的:
树状数组结构
是不是已经有些明白了?这里我们我们把 B B B当作树状数组的内部存储,则据图可知:

  • B 1 = A 1 B_1=A_1 B1=A1
  • B 2 = A 1 + A 2 B_2=A_1+A_2 B2=A1+A2
  • B 3 = A 3 B_3=A_3 B3=A3
  • B 4 = A 1 + A 2 + A 3 + A 4 B_4=A_1+A_2+A_3+A_4 B4=A1+A2+A3+A4
  • B 5 = A 5 B_5=A_5 B5=A5
  • B 6 = A 5 + A 6 B_6=A_5+A_6 B6=A5+A6
  • B 7 = A 7 B_7=A_7 B7=A7
  • B 8 = A 1 + A 2 + A 3 + A 4 + A 5 + A 6 + A 7 + A 8 B_8=A_1+A_2+A_3+A_4+A_5+A_6+A_7+A_8 B8=A1+
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值