2016-09-16 13 views
1

私はPythonで少しOOPを実験しましたが、データ構造上で宿題をしていましたが、修正方法を継承する方法を理解する上でいくつかの問題があります。正しい方法で1つの修正を継承する

class BinarySearchTree(object): 
    # snipped 
    def _insert(self, key, val): 
     prevNode = None 
     currentNode = self.root 
     while currentNode: 
      prevNode = currentNode 
      if key < currentNode.key: 
       currentNode = currentNode.leftChild 
      else: 
       currentNode = currentNode.rightChild 

     if key < prevNode.key:      
      prevNode.leftChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.leftChild)    
     else:          
      prevNode.rightChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.rightChild) 
    # snipped     

そして:

だから、私が持っている

class RBTree(BinarySearchTree): 
    # snipped 
    def _insert(self, key, val): 
     prevNode = None 
     currentNode = self.root 
     while currentNode: 
      prevNode = currentNode 
      prevNode.size += 1 # The only difference is in this line 
      if key < currentNode.key: 
       currentNode = currentNode.leftChild 
      else: 
       currentNode = currentNode.rightChild 

     if key < prevNode.key:      
      prevNode.leftChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.leftChild)    
     else:          
      prevNode.rightChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.rightChild) 
    # snipped 

をそして、私の質問があります:このメソッドを継承し、全体をコピーせずに、この1差(prevNode.size += 1)を実現するスマートな方法があります継承された関数コード?

P .:私の悪い英語のために申し訳ありません。

UPD:今、私は

+1

いいえこれはあなたがそれをするために。ノードを一度しか変更していない場合は、それが一つのことになりますが、ループしているので、メソッドを再実装する必要があります。 –

+0

'prevNode.size + = self.something'を設定し、それを適切に(デフォルトでは' 0'に)設定することができます。 – jonrsharpe

+1

[懸念の分離](https://en.wikipedia.org/wiki/Separation_of_concerns)では、ツリークラスのコードでノードを管理する必要があります。これを行う良い方法は訪問者のデザインパターンです。 – CAB

答えて

1

prevNodeBTreeRBTreeであると仮定すると...スコットとCABのソリューションの間で選択することはできません、あなたは「updateSize`を言って、別の方法を追加し、ラインを含めることができ

prevNode.updateSize() 

BTreeでは、これは何も行いません。しかし、RBTreeをサブクラスBTReeにすると、このメソッドをオーバーライドして、ノードのサイズに1を加えることができます。

1

ここでは、ビジターデザインパターンを使用した提案があります。

このパターンでは、訪れた各ノードで何を行う必要があるかを具体的に知っている訪問者の方法を書いています。

訪問者機能を追加するように基本クラスを変更します。

class BinarySearchTree(object): 
# snipped 
def _insert(self, key, val, visitor=None): # Change here 
    prevNode = None 
    currentNode = self.root 
    while currentNode: 
     prevNode = currentNode 
     if visitor: visitor(prevNode)  # Change here 
     if key < currentNode.key: 
      currentNode = currentNode.leftChild 
     else: 
      currentNode = currentNode.rightChild 

    if key < prevNode.key:      
     prevNode.leftChild = self.Node(key, val, parent=prevNode) 
     self.updateNodeProperties(prevNode.leftChild)    
    else:          
     prevNode.rightChild = self.Node(key, val, parent=prevNode) 
     self.updateNodeProperties(prevNode.rightChild) 
# snipped 

ここでは2番目のクラスです。

class RBTree(BinarySearchTree): 
# snipped 
def _insert(self, key, val): 
    visitor = lambda node: node.size += 1 
    super(RBTree, self)._insert(self, key, val, visitor) 
# snipped 
+0

Big thx、しかし、あなたが答えを書いている間、私は元の投稿へのあなたのコメントのために同じことをしました:) – KgOfHedgehogs

2

それはまさにエレガントではないのですが、あなたはこのような何か行うことができます:それはdoesnのインスタンス変数を更新するために、あなたのBinarySearchTreeクラスのコードを持っているので、私は、本当に好きではない

class BinarySearchTree(object): 
    def _insert(self, key, val, update=False): 
     prevNode = None 
     currentNode = self.root 
     while currentNode: 
      prevNode = currentNode 
      if update: 
       prevNode.size += 1 
      if key < currentNode.key: 
       currentNode = currentNode.leftChild 
      else: 
       currentNode = currentNode.rightChild 

     if key < prevNode.key:      
      prevNode.leftChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.leftChild)    
     else:          
      prevNode.rightChild = self.Node(key, val, parent=prevNode) 
      self.updateNodeProperties(prevNode.rightChild) 
    # snipped 

class RBTree(BinarySearchTree): 
    # snipped 

    def _insert(self, key, val): 
     super(RBTree, self)._insert(self, key, val, update=True) 

を派生したRBTreeクラス以外の部分は存在しますが、BinarySearchTreeインスタンスでコードのその部分が実行されるべきではないので、NameError ...

関連する問題