我正在尝试并行化一些执行一些递归线性方程的软件。我认为其中一些可能会改编成前缀和。下面是几个我正在处理的方程式的例子。
标准前缀总和定义为:
y[i] = y[i-1] + x[i]
我感兴趣的一个方程看起来像前缀和,但是有一个乘法:
y[i] = A*y[i-1] + x[i]
另一个具有更深层次的递归:
y[i] = y[i-1] + y[i-2] + x[i]
除了解决这两种变化的方法外,我想知道是否有资源涵盖如何将上述问题改编成前缀和形式。或更一般而言,采用前缀总和以使其更灵活的技术。
答案 0 :(得分:1)
(1)
y[i] = A*y[i-1] + x[i]
可以写为
y[z] = A^z * y[0] + Sum(A^(z-j) * x[j])
,where j E [z,1].
A^z * y[0]
可以在O(log(z))
Sum(A^(z-j) * x[j])
可以在O(z)
中计算。
如果预先知道序列的最大大小(例如max
),则可以将x
的修改后的前缀和数组预先计算为
prefix_x[i] = A*prefix_x[i-1] + x[i]
then Sum(A^(z-j) * x[j]) is simply prefix_x[z]
and the query becomes O(1) with O(max) precomputation.
(2)
y[i] = y[i-1] + y[i-2] + x[i]
可以写为
y[z] = (F[z] * y[1] + F[z-1] * y[0]) + Sum(F[z-j+1] * x[j])
,where j E [z,2] and F[x] = xth fibonaci number
(F[z] * y[1] + F[z-1] * y[0])
可以在O(log(z))
Sum(F[z-j+1] * x[j])
可以在O(z)
中计算。
如果预先知道序列的最大大小(例如max
),则可以将x的修改后的前缀和数组预先计算为
prefix_x[i] = prefix_x[i-1] + prefix_x[i-2] + x[i]
then Sum(F[z-j+1] * x[j]) is simply prefix_x[z]
and the query becomes O(1) with O(max) precomputation.