【发布时间】:2021-11-16 23:44:36
【问题描述】:
对于一个全南列表a = [np.nan, np.nan],a.index(np.nan) 返回0,而对于b = np.nanmax(a) 返回的np.nan,a.index(b) 给出一个ValueError。 np.nan 和 b 的对象 id 不同。但是,如果a 是[2,3.1] 和c = np.array(a).tolist(),那么id(a[1]) 和id(c[1]) 也会不同,但a.index(c[1]) 没有ValueError?
list.index() 如何在后台工作?它是否比较值相等(我猜不是,否则a.index(np.nan) 应该返回错误,因为np.nan != np.nan)?对于对象 id(我想不是,否则 a.index(c[1]) 应该返回错误)?为什么a.index(np.nanmax(a)) 的示例在a = [np.nan,np.nan] 下不起作用,而a.index(np.nan) 可以?
import numpy as np
a = [np.nan, np.nan]
b = np.nanmax(a)
print(id(np.nan), id(a[0]), id(a[1]), id(b))
a.index(np.nan)
a.index(b)
# Output:
# 47021195940144 47021195940144 47021195940144 47021566155984
# ...
# File "<ipython-input-2-fb7cc8fa88c0>", line 9, in <module>
# a.index(b)
# ValueError: nan is not in list
【问题讨论】:
-
如果你查看
type(np.nan) == type(b),那么你会得到False:type(np.nan)是<class 'float'>而type(b)是<class 'numpy.float64'>。为什么会发生这种情况:np.nanmax确实通过a = np.asanyarray(a)将类似数组的a转换为ndarray,并且这种转换会产生dtypenp.float64的ndarry,它在输出中被保留。 -
@Timus 关于不同类型的好点,但我猜作者询问
index的实现@ 即How does list.index() work under the hood? -
@0dminnimda 也许,也许不是。 :)) 我怀疑这个问题是由于误解
np.nan和b只是具有不同的值/本质上是不同的对象,因此b不是a的元素,这使得结果a.index(b)很明显。但谁知道呢......无论如何,我没有将它作为答案发布,只是作为评论 - 我认为这就是 cmets 的用途。 -
@0dminnimda:是的,我只是想了解为什么
float(3.1)示例有效,尽管在列表-数组-列表转换之后是一个不同的对象,以及为什么np.nan示例有效,尽管没有与np.nan相等。您在下面的回答中澄清了这一点。我不认为list.index会同时测试x is y(参考)和x == y,但考虑到代码输出是合乎逻辑的。