4

我正在尝试创建一个填充了一个对象的 NumPy 数组,我想知道是否有一种方法可以向整个数组广播,以便每个对象执行某些操作。

代码:

class player:
    def __init__(self,num = 5):
        self.num = num

    def printnum():
        print(self.num)
...

objs = np.array([player(5),player(6)],dtype=Object)
objs.printnum()

就目前而言,这会返回一个错误。我尝试按照手册将 dtype 更改为:_object,但似乎没有任何效果。

4

2 回答 2

2

一个 numpy 对象数组不继承该对象的方法。ndarray方法通常作用于整个数组

这也不适用于内置类型,例如:

In [122]: import numpy as np

In [123]: n = 4.0

In [124]: a = np.arange(n)

In [125]: n.is_integer()
Out[125]: True

In [126]: a.is_integer()
---------------------------------------------------------------------------
AttributeError: 'numpy.ndarray' object has no attribute 'is_integer'

Numpy 广播是使用元素运算符完成的,例如添加:

In [127]: n
Out[127]: 4.0

In [128]: a
Out[128]: array([ 0.,  1.,  2.,  3.])

In [129]: n + a
Out[129]: array([ 4.,  5.,  6.,  7.])

如果您想基本上调用print数组中的所有元素,您可以简单地重新定义.__repr__()print. 我会提醒您,通过覆盖该方法会丢失信息。

In [148]: class player:
   .....:     def __init__(self, num=5):
   .....:         self.num = num
   .....:     def __repr__(self):
   .....:         return str(self.num)
   .....:     

In [149]: objs = np.array([player(5), player(6)])

In [150]: objs
Out[150]: array([5, 6], dtype=object)

In [151]: print objs
[5 6]

即使它看起来像,但这并不相同np.array([5,6])

In [152]: objs * 3
----------------------
TypeError: unsupported operand type(s) for *: 'instance' and 'int'

在那里你可以看到覆盖的缺点__repr__

更简单的方法是使用您当前的printnum()方法,但在循环中调用它:

In [164]: class player:
   .....:     def __init__(self, num=5):
   .....:         self.num = num
   .....:     def printnum(self):
   .....:         print(self.num)
   .....:         

In [165]: for p in objs:
   .....:     p.printnum()
   .....:
5
6

或者,也许定义您的方法以返回一个字符串而不是打印一个,然后进行列表理解:

In [169]: class player:
   .....:     def __init__(self, num=5):
   .....:         self.num = num
   .....:     def printnum(self):
   .....:         return str(self.num)
   .....: 

In [170]: objs = np.array([player(5), player(6)])

In [171]: [p.printnum() for p in objs]
Out[171]: ['5', '6']
于 2013-04-04T15:49:20.067 回答
1

代码中的几个拼写错误:printnum()需要selfarg 和Object->object

class player:
    def __init__(self, num=5):
        self.num = num

    def printnum(self):
        print(self.num)


objs = np.array([player(5),player(6)], dtype=object)

# It's not a "broadcast" (what you mean is map), but it has the same result
# plus it's pythonic (explicit + readable)
for o in objs:
    o.printnum()

看起来您真正想要做的是创建一个生成器对象。谷歌python generator yield,你会得到一些这样的例子

于 2013-04-04T04:50:16.933 回答