保持numpy ndarray子类作为转换期间的返回值.安全设置__array_priority__?

Wil*_*uck 6 python arrays numpy subclass

我试图子类numpyndarray类,并且已经取得了一些运气.我想要的行为几乎与文档中给出的示例完全相同.我想name在数组中添加一个参数(我用它来跟踪数据最初的来源).

class Template(np.ndarray):
    """A subclass of numpy's n dimensional array that allows for a
    reference back to the name of the template it came from.
    """
    def __new__(cls, input_array, name=None):
        obj = np.asarray(input_array).view(cls)
        obj.name = name
        return obj

    def __array_finalize__(self, obj):
        if obj is None: return
        self.name = getattr(obj, 'name', None)
Run Code Online (Sandbox Code Playgroud)

这是有效的,除了像这个问题一样,我想要任何涉及我的子类的转换来返回我的子类的另一个实例.

有时numpy函数会返回以下实例Template:

>>> a = Template(np.array([[1,2,3], [2,4,6]], name='from here')
>>> np.dot(a, np.array([[1,0,0],[0,1,0],[0,0,1]]))
Template([[1, 2, 3],
       [2, 4, 6]])
Run Code Online (Sandbox Code Playgroud)

但是,有时它们不会:

>>> np.dot(np.array([[1,0],[0,1]]), a)
array([[1, 2, 3],
       [2, 4, 6]])
Run Code Online (Sandbox Code Playgroud)

在我上面链接的问题中,有人建议OP应该覆盖__wrap_array__子类的方法.但是,我认为没有任何理由.在某些情况下,我使用默认值获得预期的行为__array_wrap__.文档似乎表明我遇到的情况__array_wrap__是由于更高的__array_priority__值而被调用的另一个参数的方法:

请注意,ufunc(np.add)已调用__array_wrap__具有最高__array_priority__值的输入方法

所以我的问题有几个相关的部分.首先:我可以设置__array_priority__我的子类的属性,以便__array_wrap__始终调用它的属性吗?第二:这是实现我想要的行为的最好/最简单的方法吗?

cch*_*lis 0

当两个对象具有相同的 __array_priority__ 时:

>>> np.array([[1,0],[0,1]]).__array_priority__
0.0
>>> a.__array_priority__
0.0
Run Code Online (Sandbox Code Playgroud)

并且只能使用一个对象的方法,通过使用第一个数组/对象的方法来解决平局。(在你的情况下 __array_wrap__ )

从这个问题来看,您的类的方法似乎应该始终是首选,因为它们是相同的(通过继承)或被重写。

所以我会调高 __array_priority__ 。

class Template(np.ndarray):
    __array_priority__ = 1.0 (Or whichever value is high enough)
    ...
Run Code Online (Sandbox Code Playgroud)

执行此操作后,无论模板对象位于计算中的哪个位置。它的方法将优于标准数组的方法。