- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
所以这是关于我假设的两个问题与我的基本相同的基本混淆。我希望没关系。
这里有一些代码:
import numpy as np
class new_array(np.ndarray):
def __new__(cls, array, foo):
obj = array.view(cls)
obj.foo = foo
return obj
def __array_finalize__(self, obj):
print "__array_finalize"
if obj is None: return
self.foo = getattr(obj, 'foo', None)
def __getitem__(self, key):
print "__getitem__"
print "key is %s"%repr(key)
print "self.foo is %d, self.view(np.ndarray) is %s"%(
self.foo,
repr(self.view(np.ndarray))
)
self.foo += 1
return super(new_array, self).__getitem__(key)
print "Block 1"
print "Object construction calls"
base_array = np.arange(20).reshape(4,5)
print "base_array is %s"%repr(base_array)
p = new_array(base_array, 0)
print "\n\n"
print "Block 2"
print "Call sequence for p[-1:] is:"
p[-1:]
print "p[-1].foo is %d\n\n"%p.foo
print "Block 3"
print "Call sequence for s = p[-1:] is:"
s = p[-1:]
print "p[-1].foo is now %d"%p.foo
print "s.foo is now %d"%s.foo
print "s.foo + p.foo = %d\n\n"%(s.foo + p.foo)
print "Block 4"
print "Doing q = s + s"
q = s + s
print "q.foo = %d\n\n"%q.foo
print "Block 5"
print "Printing s"
print repr(s)
print "p.foo is now %d"%p.foo
print "s.foo is now %d\n\n"%s.foo
print "Block 6"
print "Printing q"
print repr(q)
print "p.foo is now %d"%p.foo
print "s.foo is now %d"%s.foo
print "q.foo is now %d\n\n"%q.foo
print "Block 7"
print "Call sequence for p[-1]"
a = p[-1]
print "p[-1].foo is %d\n\n"%a.foo
print "Block 8"
print "Call sequence for p[slice(-1, None, None)] is:"
a = p[slice(-1, None, None)]
print "p[slice(None, -1, None)].foo is %d"%a.foo
print "p.foo is %d"%p.foo
print "s.foo + p.foo = %d\n\n"%(s.foo + p.foo)
Block 1
Object construction calls
base_array is array([[ 0, 1, 2, 3, 4],
[ 5, 6, 7, 8, 9],
[10, 11, 12, 13, 14],
[15, 16, 17, 18, 19]])
__array_finalize
Block 2
Call sequence for p[-1:] is:
__array_finalize
p[-1].foo is 0
Block 3
Call sequence for s = p[-1:] is:
__array_finalize
p[-1].foo is now 0
s.foo is now 0
s.foo + p.foo = 0
Block 4
Doing q = s + s
__array_finalize
q.foo = 0
Block 5
Printing s
__getitem__
key is -1
self.foo is 0, self.view(np.ndarray) is array([[15, 16, 17, 18, 19]])
__array_finalize
__getitem__
key is -5
self.foo is 1, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__getitem__
key is -4
self.foo is 2, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__getitem__
key is -3
self.foo is 3, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__getitem__
key is -2
self.foo is 4, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__getitem__
key is -1
self.foo is 5, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
new_array([[15, 16, 17, 18, 19]])
p.foo is now 0
s.foo is now 1
Block 6
Printing q
__getitem__
key is -1
self.foo is 0, self.view(np.ndarray) is array([[30, 32, 34, 36, 38]])
__array_finalize
__getitem__
key is -5
self.foo is 1, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__getitem__
key is -4
self.foo is 2, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__getitem__
key is -3
self.foo is 3, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__getitem__
key is -2
self.foo is 4, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__getitem__
key is -1
self.foo is 5, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
new_array([[30, 32, 34, 36, 38]])
p.foo is now 0
s.foo is now 1
q.foo is now 1
Block 7
Call sequence for p[-1]
__getitem__
key is -1
self.foo is 0, self.view(np.ndarray) is array([[ 0, 1, 2, 3, 4],
[ 5, 6, 7, 8, 9],
[10, 11, 12, 13, 14],
[15, 16, 17, 18, 19]])
__array_finalize
p[-1].foo is 1
Block 8
Call sequence for p[slice(-1, None, None)] is:
__getitem__
key is slice(-1, None, None)
self.foo is 1, self.view(np.ndarray) is array([[ 0, 1, 2, 3, 4],
[ 5, 6, 7, 8, 9],
[10, 11, 12, 13, 14],
[15, 16, 17, 18, 19]])
__array_finalize
p[slice(None, -1, None)].foo is 2
p.foo is 2
s.foo + p.foo = 3
p[-1:]
不会导致调用 new_array.__getitem__
.如果 p[-1:]
,这是真的被 p[0:]
之类的东西取代, p[0:-1]
,等等...但是像 p[-1]
这样的语句和 p[slice(-1, None, None)]
确实导致调用 new_array.__getitem__
.对于像 p[-1:] + p[-1:]
这样的语句也是如此。或 s = p[-1]
但对于像 print s
这样的语句来说不是这样的.您可以通过查看上面给出的“ block ”来看到这一点。 foo
在调用 new_array.__getitem__
期间正确更新(参见 block 5 和 6)但一旦评估 new_array.__getitem__
就不正确已完成(再次参见 block 5 和 block 6)。我还应该添加替换行 return super(new_array, self).__getitem__(key)
与 return new_array(np.array(self.view(np.ndarray)[key]), self.foo)
也不起作用。以下 block 是输出的唯一区别。Block 5
Printing s
__getitem__
key is -1
self.foo is 0, self.view(np.ndarray) is array([[15, 16, 17, 18, 19]])
__array_finalize__
__getitem__
key is -5
self.foo is 1, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -4
self.foo is 2, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -3
self.foo is 3, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -2
self.foo is 4, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -1
self.foo is 5, self.view(np.ndarray) is array([15, 16, 17, 18, 19])
__array_finalize__
__array_finalize__
__array_finalize__
new_array([[15, 16, 17, 18, 19]])
p.foo is now 0
s.foo is now 1
Block 6
Printing q
__getitem__
key is -1
self.foo is 0, self.view(np.ndarray) is array([[30, 32, 34, 36, 38]])
__array_finalize__
__getitem__
key is -5
self.foo is 1, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -4
self.foo is 2, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -3
self.foo is 3, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -2
self.foo is 4, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__array_finalize__
__array_finalize__
__array_finalize__
__getitem__
key is -1
self.foo is 5, self.view(np.ndarray) is array([30, 32, 34, 36, 38])
__array_finalize__
__array_finalize__
__array_finalize__
new_array([[30, 32, 34, 36, 38]])
p.foo is now 0
s.foo is now 1
q.foo is now 1
new_array.__array_finalize__
的过多调用,但没有foo
改变“问题” . p[-1:]
这样的电话到 new_array
对象 p.foo = 0
将导致此语句 p.foo == 1
返回 True
.显然事实并非如此,即使 foo
在调用 __getitem__
期间被正确更新, 因为像 p[-1:]
这样的语句导致对 __getitem__
的大量调用(一旦考虑到延迟评估)。另外来电p[-1:]
和 p[slice(-1, None, None)]
将导致 foo
的不同值(如果计数工作正常)。在前一种情况下 foo
本来会有 5
添加到它,而在后一种情况下 foo
本来会有 1
添加到它。 __getitem__
评估应该返回什么类型的对象。在某些情况下,它返回相同类型的新实例,在其他情况下,它返回某个其他类型的新实例,在其他情况下,它返回一个 numpy 数组、标量或浮点数(取决于底层 numpy 数组认为是正确的) )。我使用传递给
__getitem__
的 key 确定要返回的正确对象是什么。但是如果用户传递了一个切片,我就不能这样做,例如类似
p[-1:]
,因为该方法只获取单个索引,例如好像用户写了
p[4]
.
那么如果 key
我该怎么做呢?在 __getitem__
我的 numpy 子类没有反射(reflect)用户是否请求切片,由 p[-1:]
给出,或者只是一个条目,由 p[4]
给出?
slice(start, stop, step)
将被视为与
start:stop:step
之类的语句相同.这让我觉得我错过了一些非常基本的东西。暗示这一点的句子很早就出现了:
Basic slicing occurs when obj is a slice object (constructed by start:stop:step notation inside of brackets), an integer, or a tuple of slice objects and integers.
self.foo += 1
的原因。行应该计算用户请求切片或
new_array
实例的元素的次数。 (而不是切片“中”的元素数量)。
这两个问题实际上是否相关,如果是,如何相关?
最佳答案
你确实被一个讨厌的错误咬了。知道我不是唯一的人,真是一种解脱!幸运的是,它很容易解决。只需在您的类(class)中添加如下内容即可。这实际上是我几个月前写的一些代码的复制粘贴,文档字符串告诉了发生了什么,但你可能想阅读 the python docs以及。
def __getslice__(self, start, stop) :
"""This solves a subtle bug, where __getitem__ is not called, and all
the dimensional checking not done, when a slice of only the first
dimension is taken, e.g. a[1:3]. From the Python docs:
Deprecated since version 2.0: Support slice objects as parameters
to the __getitem__() method. (However, built-in types in CPython
currently still implement __getslice__(). Therefore, you have to
override it in derived classes when implementing slicing.)
"""
return self.__getitem__(slice(start, stop))
关于python - Numpy __getitem__ 延迟评估和 a[-1 :] not the same as a[slice(-1, None, none)],我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14553485/
这个问题在这里已经有了答案: Why does the print function return None? (1 个回答) 关闭 6 年前。 我正在学习理解。我得到了 print(x) 部分(我
我以为我理解了 Python 中的这两个单例值,直到我看到有人在代码中使用 return l1 or l2,其中 l1 和 l2 都是链表对象,并且(s)他想如果不为 None 则返回 l1,否则返回
我希望在 IPython Notebook 中使用列表理解生成枚举字符串列表。它有效,但给了我一个我不理解的奇怪输出。 cols = [] [cols.append('Value'+str(hour)
这个问题在这里已经有了答案: Why does the expression 0 >> import dis >>> def a(): ... return None is None is N
《Learning Python 5th》第608页有示例代码: >>> list(print(x.upper(), end=' ') for x in 'spam') S P A M [None,
我对此进行了搜索并遇到了列表返回函数,但我仍然不明白。 我试图理解为什么 Print 函数到另一个函数返回以下内容: 生日快乐 生日快乐 无 无 我的代码: def happy(): prin
除非我疯了 if None not in x 和 if not None in x 是等价的。有首选版本吗?我想 None not in 更像英语,因此更像 pythonic,但 not None i
尝试绘制 k-NN 分类器的决策边界但无法这样做得到 TypeError: '(slice(None, None, None), 0)' is an invalid key h = .01 # st
我正在尝试将可变大小的序列输入 LSTM。因此我使用生成器且批量大小为 1。 我有一个嵌入的 (sequence_length,)-input-tensor,并输出 (batch_size,equen
这个问题在这里已经有了答案: 关闭 10 年前。 Possible Duplicate: Is there any way to know if the value of an argument i
我正在尝试根据环境变量的返回值进行条件赋值。 self._TBLFilePath = iTBLFilePath or os.environ.get("CDO_TBLPATH") + os.enviro
我正在使用 marshmallow 2.0.0rc2 验证 HTTP 请求的输入数据,并在 HTTP 响应上将 SQLAlchemy 模型加载到 JSON。我偶然发现了两个问题: 首先,在通过 HTT
我想将我设置为 None 的变量与 is 进行比较,但它失败了。 当我使用 == 将此变量与 None 进行比较时,它起作用了。 这就是我所说的变量: print type(xml.a) -> 因为
我最近遇到了这种语法,我不知道有什么区别。 如果有人能告诉我其中的区别,我将不胜感激。 最佳答案 答案解释here . 引用: A class is free to implement compari
尝试使用 BorutaPy 进行特征选择。但出现 TypeError: '(slice(None, None, None), array([0, 1, 2, 3, 4]))' 是无效键。 from s
我见过使用 [] 的代码片段, [None] , None或 ()作为 placeholder 的形状, 那是 x = tf.placeholder(..., shape=[], ...) y = t
是否有逻辑推理可以解释为什么下面的 Ansible playbook 中的两个 debug 任务分别输出 "NONE" 和 "FALSE"并且不是两者都“NONE”? - hosts: 'all'
我有一个函数,它可以返回两个整数的元组或(None, None)的元组: (出于本问题的目的,我们假设此返回格式是执行此操作的唯一方法,并且无法更改) from typing import Tuple
问题: 如何遍历字典并从中删除 None 键或值? 这是我尝试过的: 代码: import copy def _ignore(data): copied_data = copy.deepcop
什么是简洁的 python 表达方式 if : # do a bunch of stuff once 最佳答案 为什么不简单, None not in lst 关于python - 简明地说 "
我是一名优秀的程序员,十分优秀!