【问题标题】:checking if a min heap array is valid检查最小堆数组是否有效
【发布时间】:2021-05-03 22:43:02
【问题描述】:

我有这个函数 def validate(self) 应该检查给定数组是否是有效的最小堆。我认为它有效,但因为我的数组在开头没有像 [None, 2, 3, 5] 这样的数组,它似乎遇到了问题并给我错误'<' not supported between instances of 'int' and 'NoneType'

如何跳过代码中的 none 值?

def validate(self):
    """
    Validates the heap. Returns True if the heap is a valid min-heap, and
    False otherwise.

    """

    n = self.__len__() 
    for i in range(int((n - 2) / 2) + 2):

        if self._items[2 * i + 1] < self._items[i]: 
            return False

        if (2 * i + 2 < n and self._items[2 * i + 2] > self._items[i]): 
            return False
    return True

新代码:

def validate(self):
    """
    Validates the heap. Returns True if the heap is a valid min-heap, and
    False otherwise.

    """

    n = self.__len__() 
    for i in range(int((n - 2) / 2) + 2):
        if self._items[i] != None:
            if self._items[2 * i + 1] < self._items[i]: 
                return False

        if (2 * i + 2 < n and self._items[2 * i + 2] > self._items[i]): 
            return False

错误:

  File "<doctest __main__.MinHeap.validate[8]>", line 1, in <module>
    h.validate()
  File "x-wingide-python-shell://114699264/2", line 219, in validate
TypeError: '>' not supported between instances of 'int' and 'NoneType'

【问题讨论】:

  • None 不能与其他元素进行比较,因此它不应该是堆数组的一部分。我认为生成的二叉树是不平衡的……
  • 在使用数组实现堆时,根节点可以位于索引 0 或 1 处,即Why in a heap implemented by array the index 0 is left unused。由于 None 位于索引 0 处,这似乎根节点位于索引 1 处,因此应相应地检查数组。

标签: python min-heap


【解决方案1】:

与检查每个非叶节点的左孩子和右孩子(如果有的话)相比,检查每个非根节点与其父节点更简单。

def validate(self):
    n = len(self._items)
    for i in range(2, n):
        if self._items[i // 2] > self._items[i]: 
            return False
    return True

您还可以使用 all 的推导:

def validate(self):
    n = len(self._items)
    return all(self._items(i // 2) <= self._items[i] for i in range(2, n))

【讨论】:

    【解决方案2】:

    改变

        for i in range(int((n - 2) / 2) + 2):
            if self._items[2 * i + 1] < self._items[i]
                return False
    
            if (2 * i + 2 < n and self._items[2 * i + 2] > self._items[i]): 
                return False
    

        _items = list(filter(None, self._items)) # delete all Nones in the list, save the cleaned list into a local variable in case you want to use the unmodified list somewhere else
        for i in range(int((n - 2) / 2) + 2):
            if _items[2 * i + 1] < _items[i]: 
                return False
    
            if (2 * i + 2 < n and _items[2 * i + 2] > _items[i]): 
                return False
    

    这样,它会先从列表中删除所有的无,然后才进行比较。

    【讨论】:

    • 嗯,这仍然给我 NoneTpe 错误
    • @MangoLemon 然后请发布完整和准确的回溯,而不仅仅是最后一行的一部分
    猜你喜欢
    • 1970-01-01
    • 2011-05-08
    • 2019-01-06
    • 1970-01-01
    • 1970-01-01
    • 2022-08-07
    • 2020-09-11
    • 2021-04-28
    • 2012-11-30
    相关资源
    最近更新 更多