第二十九天(树状数组)(二叉搜索树)
今天完成题目:307,1038 307:区域和检索-数组可修改
class NumArray:
def __init__(self, nums: List[int]):
'''初始化,总时间 O(n)'''
self._nums = [0] + nums # 树状数组
n = len(nums)
# 初始化
for i in range(1, n + 1):
j = i + self.lowbit(i) # 寻找父结点
if j < n + 1:
self._nums[j] += self._nums[i] # 父结点的值=子结点的值的和
def lowbit(self, x: int) -> int:
'''低位计数:返回最小一位1的值,例如0b0010返回0b10'''
return x & (-x)
def update(self, idx: int, val: int):
'''将原数组idx下标更新为val, 总时间O(log n)'''
prev = self.sumRange(idx, idx) # 计算出原来的值
idx += 1 # 下标从1开始
val -= prev # val 是要增加的值,可正可负
while idx < len(self._nums): #修改自己及其父结点的值
self._nums[idx] += val
idx += self.lowbit(idx)
def _query(self, idx: int) -> int:
'''计算数组[0, idx)的元素之和'''
res = 0
while idx > 0:
res += self._nums[idx]
idx -= self.lowbit(idx) # 寻找儿子结点
return res
def sumRange(self, i: int, j: int) -> int:
'''返回数组[begin, end] 的和'''
return self._query(j+1) - self._query(i)
# Your NumArray object will be instantiated and called as such:
# obj = NumArray(nums)
# obj.update(i,val)
# param_2 = obj.sumRange(i,j)
1038:从二叉树到更大和树
反向中序遍历记录较大值的和
最后更新于
这有帮助吗?