特别是,我不明白这部分代码的原因或原因
s += a[i];
total += query(s);
update(s);
允许您计算每个点左下象限中的总点数。
有人可以详细说明吗?
答案 0 :(得分:1)
作为飞机问题的类比,请考虑一下:
*当前点指的是您引用的for循环的当前迭代中考虑的点,即(i,P [i])
让我们定义另一个数组,C [s]:
C[s] = Number of Prefix Sums of array A[1..(i - 1)] that amount to s
因此,#3的解成为总和... C [-2] + C [-1] + C [0] + C [1] + C [2] ... C [P [i] - 1],即C [P [i]]
的前缀和使用BIT存储C的前缀和,从而将查询定义为:
query(s) = Number of Prefix Sums of array A[1..(i - 1)] that amount to a value < s
使用这些定义,给定代码中的s为您提供了当前索引i(P [i])的前缀总和。 total构建答案,更新只是将P [i]添加到BIT。
我们必须为所有i重复此方法,因此for循环。
PS:它使用称为二进制索引树(http://community.topcoder.com/tc?module=Static&d1=tutorials&d2=binaryIndexedTrees)的数据结构进行操作。如果您不熟悉它,我建议您检查链接。
编辑: 您将获得一个数组S和一个值X.您可以将S分成两个不相交的子数组,使得L的所有元素都小于X,而H则包含大于或等于X的元素。
A: All elements of L are less than all elements of H.
S的任何子序列T将具有L的一些元素和H的一些元素。假设它具有L的L和q的p元素。当T被分类以给出T'时,L的所有p元素出现在q由于A的H元素。
Median being the central value is the value at location m = (p + q)/2
直觉上认为q> = p意味着中位数位于X中,作为证据: T'中位置[1..p]的值属于L.因此,如果中位数为H,则位置m应大于p:
m > p
(p + q)/2 > p
p + q > 2p
q > p
B: q - p > 0
对于计算机q - p,我将T'中的所有元素替换为-1(如果它们属于L(&lt; X))则+1,如果它们属于H(&gt; = X) T看起来像{-1,-1,-1 ... 1,1,1} 它有p次-1和q次1.T'的总和现在给我:
Sum = p * (-1) + q * (1)
C: Sum = q - p
我可以使用此信息在B中找到值。
所有子序列的形式为{A [i],A [i + 2],A [i + 3] ... A [j + 1]},因为它们是连续的,计算A [i的总和]到A [j + 1],我可以用P [i] = A [1] + A [2] + A [i - 1]计算A [i]的前缀和 从A [i]到A [j]的子序列之和则可以计算为P [j] - P [i](j大于j和i) 考虑到C和B,我们得出结论:
Sum = P[j] - P[i] = q - p (q - p > 0)
P[j] - P[i] > 0
P[j] > P[i]
j&gt;我和P [j]&gt;每个解决方案的P [i]给出中值&gt; = X
总结: