簡體   English   中英

在 Python 中迭代刪除二叉搜索樹中的值

[英]Deleting a value in a Binary Search Tree iteratively in Python

我目前正在學習一門學習數據結構和算法的課程,我正在學習 BST。 我已經讓代碼可以工作並理解其中的大部分內容,但是我有一個關於刪除功能的問題。 這是我的代碼的樣子:

class BST:
    def __init__(self, value):
        self.value = value
        self.left = None
        self.right = None

    def insert(self, value):
        currentNode = self

        while True:
            if value < currentNode.value:
                if currentNode.left is None:
                    currentNode.left = BST(value)
                    break
                else:
                    currentNode = currentNode.left
            else:
                if currentNode.right is None:
                    currentNode.right = BST(value)
                    break
                else:
                    currentNode = currentNode.right
        return self

    def contains(self, value):
        currentNode = self

        while currentNode is not None:
            if value < currentNode.value:
                currentNode = currentNode.left
            elif value > currentNode.value:
                currentNode = currentNode.right
            else:
                return True
        return False

    def remove(self, value, parentNode = None):
        currentNode = self

        while currentNode is not None:
            if value < currentNode.value:
                parentNode = currentNode
                currentNode = currentNode.left  
            elif value > currentNode.value:
                parentNode = currentNode
                currentNode = currentNode.right
            #Found the node
            else:   
            #two child ondes
                if currentNode.left is not None and currentNode.right is not None:
                    currentNode.value = currentNode.right.getMinValue()      #get the left number from the right subtree
                    currentNode.right.remove(currentNode.value, currentNode) #remove that most left number by using remove() 
                                                                             #on the right currentNode
                #root node
                elif parentNode is None:
                    if currentNode.left is not None:
                        currentNode.value = currentNode.left.value
                        currentNode.right = currentNode.left.right
                        currentNode.left = currentNode.left.left
                    elif currentNode.right is not None:
                        currentNode.value = currentNode.right.value
                        currentNode.left = currentNode.right.left
                        currentNode.right = currentNode.right.right
                    #only 1 item left in BST
                    else:
                        pass
                #one child node
                elif parentNode.left == currentNode:
                    parentNode.left = currentNode.left if currentNode.left is not None else currentNode.right
                elif parentNode.right == currentNode:
                    parentNode.right = currentNode.left if currentNode.left is not None else currentNode.right
                break
        return self

    def getMinValue(self):
        currentNode = self

        while currentNode.left is not None:
            currentNode = currentNode.left
        return currentNode.value

我明白,對於刪除功能:

  1. while循環將遍歷每個節點並運行直到沒有更多節點
  2. 第一個ifelif用於查找您要刪除的節點。
  3. else適用於實際刪除,它有 3 個不同的選項: currentNode有兩個子節點,您只需將其替換為右側節點的最左側值,然后從右側 noe 中刪除最左側的值。 另一種情況是parentNode沒有父節點,這將是根節點的情況。 最后一種情況是當您只有一個子節點時,您所要做的就是將currentNode的值更改為其左節點或右節點(取決於它具有哪個節點)。

我不太清楚的是條件背后的邏輯,以及當我們想要刪除root時它是如何工作的。 代碼不應該也運行第一個條件,即兩個子節點的條件嗎? 我幾乎可以肯定這不應該發生,並且條件應該只針對其特殊情況運行。 我一遍又一遍地看過視頻解釋,但我就是不明白。

當我們要刪除根節點時。 代碼不應該也運行第一個條件,即兩個子節點的條件嗎?

即使在情況下,根節點必須拆除,實際評估的首要條件。 如果根節點同時具有左子節點和右子節點,則“選項 1”適用於它:第一個選項可以很好地處理任何具有兩個子節點的節點,無論它是否是根節點。 在此選項中不需要區分根節點或非根節點。

其他兩個選項僅適用於沒有兩個孩子的節點。 您似乎建議(也在代碼注釋中)只有選項 3 處理這種情況,但選項 2 也可以。 選項2是當節點節點育有兩個孩子這是根本。 如果根有 2 個孩子,它將被視為選項 1。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM