我正在尝试通过连续调用rs12 = which(rs == 12)
rs12_pm3 = 1:nrow(dd) %in% c(rs12, rs12 + 1, rs + 2, rs + 3, rs - 1, rs - 2, rs - 3)
dd[rs12_pm3, ]
来实现StreamingMedian
对象来维持中位数。为此,我还通过get_median()
模块实施了MinHeap
和MaxHeap
课程。
我遇到了一个非常奇怪的错误。出于某种原因,当我运行以下命令时:
heapq
我得到以下输出:
print("Before streaming medians", MinHeap(), sep="\t") # is empty
b = StreamingMedian()
b.add_val(5)
b.add_val(100)
assert b.get_median() == 52.5
print("After streaming medians, for MaxHeap", MaxHeap(), sep='\t') # is empty
print("After streaming medians, for MinHeap", MinHeap(), sep='\t') # should be empty
print("After streaming medians, for MinHeap with input",
MinHeap([]), sep="\t") # is empty
可以在下面找到类实现。我在Python 3.5.2 :: Anaconda自定义(64位)上运行它。
Before streaming medians []
After streaming medians, for MaxHeap []
After streaming medians, for MinHeap [100]
After streaming medians, for MinHeap with input []
答案 0 :(得分:0)
问题出现的原因是如何在python中计算默认参数。它们是在第一次调用函数时计算的,之后函数与最初计算的值一起使用。如果默认值是可变的(如列表所示),则会出现问题。
所以MinHeap
发生的事情是:
MinHeap
最初创建,l
参数默认参数已分配给内存地址。StreamingMedian
修改MinHeap
self.heap
,这与l
指向的内容相同。MinHeap
时,l
已经有一个内存地址,此内存地址将再次使用并与self.heap
绑定。 MaxHeap
不会发生这种情况,因为:
MaxHeap
最初创建,l
参数默认参数已分配给内存地址。_invert_sign
创建一个分配给self.heap
的新列表。永远不会修改默认参数l
。 MaxHeap
时,l
已经有一个内存地址并再次使用,但它从未被修改过,而且构建了另一个副本,因此永远不会修改它。 而不是:
class MinHeap(object):
def __init__(self, l=[]):
self.heap = l
heapq.heapify(l)
我们应该使用:
class MinHeap(object):
def __init__(self, l=None):
if l is None:
l = []
self.heap = l
heapq.heapify(l)
应对MaxHeap