2016-07-18 10 views
5
class Inner(): 

    def __init__(self, x): 
     self.x = x 

    def __eq__(self, other): 
     if isinstance(other, Inner): 
      return self.x == other.x 
     else: 
      raise TypeError("Incorrect type to compare") 

class Outer(): 

    def __init__(self, y): 
     self.y = Inner(y) 

    def __eq__(self, other): 
     if isinstance(other, Outer): 
      return self.y == other.y 
     elif isinstance(other, Inner): 
      return self.y == other 
     else: 
      raise TypeError("Incorrect type to compare") 


if __name__ == "__main__": 

    a = Outer(1) 
    b = Inner(1) 

    print(a == b) # ok no problem 
    print(b == a) # This will raise a type error 

In dem Beispiel habe ich innere und äußere Klasse. Ich habe keine Kontrolle darüber, welche inneren Geräte die Situation simulieren wollten. Ich habe nur die Kontrolle über Ouers Verhalten. Ich möchte, dass äußere Instanzen mit inneren Instanzen (nicht nur Gleichheit) verglichen werden können. Mit der gegebenen Implementierung funktioniert nur der erste Vergleich, weil Outer __eq__ Methode verwendet, um mit äußeren und inneren Instanzen verglichen werden kann, aber die zweite ruft Inneres __eq__, die den Vergleich mit Outer - Heck nicht wissen, dass Outer existiert Warum sollte es die Umsetzung stören? Gibt es eine Möglichkeit, die zweite Art von Vergleich zu arbeiten, mit etwas ähnlich wie die __radd__ und solche Funktionen. Ich weiß zum Beispiel in C++, dass Sie dies mit Inline-Operator-Definitionen lösen, aber wir haben solche in Python nicht.'Reversed' Vergleichsoperator in Python

Antwort

2

Um nicht zu viel Sinn: Inner.__eq__ ist kaputt. Am allerwenigsten, anstatt einen Fehler zu werfen es sollte return NotImplemented, die Python erlauben würde, den umgekehrten Vergleich zu versuchen:

Wenn NotImplemented zurückgeführt wird, wird der Interpreter dann versuchen, die Betrieb spiegelt sich auf der anderen Art, oder einige andere Fallback, je nach Betreiber. Wenn alle versuchten Operationen NotImplemented zurückgeben, löst der Interpreter eine entsprechende Ausnahme aus.

Besser noch wäre es "duck typing" zu verwenden, anstatt sich auf eine bestimmte Klasse beharren (es sei denn, der Klasse, anstatt seine Schnittstelle ist ein explizit wichtiger Bestandteil des Vergleichs):

def __eq__(self, other): 
    try: 
     return self.x == other.x 
    except AttributeError: 
     return NotImplemented 

Da Sie jedoch sagen, dass Sie dies nicht steuern können, müssen Sie ähnliche Funktionen manuell implementieren, zum Beispiel:

, da es keine __req__ in Python's data model gibt.

Verwandte Themen