2015-12-03 28 views
0

按照說明here我創建了一個ndarray的子​​類,它爲ndarray類添加了新的屬性。現在我想爲新類定義一個比較運算符,除了比較數據之外,還會比較屬性的值。所以,我想這一點:比較ndarray派生類

def __eq__(self, other): 
    return (self._prop1 == other._prop1) and \ 
      (self._prop2 == other._prop2) and \ 
      (self.data == other.data) 

這使得像T1 == T2比較,並返回一個布爾值。但是,因爲我想與其他ndarrays交替使用這些數組,我希望比較返回一個布爾數組。如果我沒有定義我的__eq__函數,那麼比較返回一個布爾數組,然後我無法檢查屬性。我怎麼能結合這兩個?

+0

看起來像'ndarray'返回標量如果屬性(例如形狀)不匹配則爲真/假,只有匹配時才返回布爾數組。使用一個或'ifs',如果它們失敗,你應該能夠返回屬性測試,'else'返回'data'測試。讓自己多次'返回'。以這種方式編寫代碼更容易。 – hpaulj

+0

@hpaulj分隔我的自定義屬性和底層數據的比較是一個很好的建議。但是,問題仍然是數據屬性本身的比較返回一個布爾值,而不是數組。我如何從比較運算符調用numpy的按元素進行比較? – deepak

+1

看看masked數組如何處理這個:'np.ma.core.MaskedArray .__ eq__' – hpaulj

回答

1

根據suggestion by hpaulj我想通過查看np.ma.core.MaskedArray.__eq__來了解如何做到這一點。這是參考的最小實現。主要想法是在DerivedArray的基類的類型中以self的視圖調用numpy __eq__()

class DerivedArray(np.ndarray): 
    def __new__(cls, input_array, prop1, prop2):  
     _baseclass = getattr(input_array, '_baseclass', type(input_array)) 
     obj = np.asarray(input_array).view(cls) 

     obj._prop1 = prop1 
     obj._prop2 = prop2 
     obj._baseclass = _baseclass 
     return obj 

    def __array_finalize__(self, obj): 
     if obj is None: 
      return 
     else: 
      if not isinstance(obj, np.ndarray): 
       _baseclass = type(obj) 
      else: 
       _baseclass = np.ndarray 

     self._prop1 = getattr(obj, '_prop1', None) 
     self._prop2 = getattr(obj, '_prop2', None) 
     self._baseclass= getattr(obj, '_baseclass', _baseclass) 

    def _get_data(self): 
     """Return the current data, as a view of the original 
     underlying data. 
     """ 
     return np.ndarray.view(self, self._baseclass) 

    _data = property(fget=_get_data) 
    data = property(fget=_get_data) 

    def __eq__(self, other): 
     attsame = (self._prop1 == other._prop1) and (self._prop2 == other._prop2) 
     if not attsame: return False 
     return self._data.__eq__(other)