当 0 除以 0 时,Pandas 无法找到 NaN

问题描述 投票:0回答:1

我有这样的数据框:

df_challenge = pd.DataFrame({'x': [1, pd.NA, 6, 9, pd.NA, 0, 9, 10, 0, 9, pd.NA, 0],
                                 'y': [0, 7.2, pd.NA, 10, 0, 1, 9.2, 10.65, pd.NA, 9, pd.NA, 0],
                                  'y_copy': [0, 7.2, np.nan, 10, 0, 1, 9.2, 10.65, np.nan, 9, np.nan,0]})

df_challenge = df_challenge.convert_dtypes()

我强行改变了其中一列的类型

df_challenge.y_copy = df_challenge.y_copy.astype('float')

我现在使用以下代码创建两个变量:

df_challenge = df_challenge.assign(z = df_challenge.x/df_challenge.y)
df_challenge = df_challenge.assign(z1 = df_challenge.x.astype('float')/df_challenge.y_copy)

现在,如果我尝试系列的 .isnull() 方法或 .isna() 方法,它不会显示 z 列的正确结果

下面的代码给出了这些结果:

df_challenge.z.isna().sum() # 5 It should be 6
df_challenge.z.isnull().sum() # 5 

df_challenge.z1.isna().sum() # 6 It is correct
df_challenge.z1.isnull().sum() # 6 

我的问题是,为什么 .isnull() 或 .isna() 在这些列中不能正确执行(或者我在这里弄错了)。不同之处在于计算涉及的数据类型不同,在 z 中(除法发生在两个(Int64/Float64,pandas 较新的数据类型)中,但是在 z1 计算中(除法发生在两个浮点数上)

现在,为了规避这个问题,而不是使用 .isna、.isnull,我尝试了使用 pandas (不是运算符 ~)的 np.isfinite,它正确地计算出 z1 中的 NAN

所以,我的第二个问题是,在 pandas 中提取此类 NAN 是否是一个好主意

这是有效的

df_challenge.loc[~df_challenge.z.pipe(np.isfinite),:]

但是,我对这种解决方法并不满意,尽管对我来说这很有效。但我想了解这一点并思考更好的解决方案。

谢谢


Pandas 版本:'2.2.2'

Python版本:Python 3.10.14

python-3.x pandas
1个回答
0
投票

1/0 是无限的 (

+inf
),因此根据 IEEE 754 的浮点约定,一个数字。numpy(和 pandas)使用 C 约定。相反,Python 除法给出的是除以零。对于大数据,最好保留 CPU(FPU)规则,而不是添加额外的计算并检查每个单元格。

您可以在以下位置获得更多信息: https://en.wikipedia.org/wiki/Floating-point_arithmetic,特别是历史和其他部分可能会让您了解为什么采用某些约定(以及何时)。

为什么?更多信息更好。对于 NaN,我们可能会丢弃该值,因为不完整的数据集,但无限会给我们带来不同的错误:我们有一些逻辑问题,我们可能会以不同的方式处理它,所以最好不要默默地丢弃。

没有正确的解决方案,最后,有人选择了一种约定(每个项目中可能有不同的约定,例如 IEEEE 754、C、python、numpy),这对于某个用例来说可能并不理想,但替代方案也有问题(在其他用例上)。别担心,通常所有这样的决定都不是轻率做出的,或者没有经过大量讨论。事实上,Python 改变了两次整数除法的含义(Python 1 到 Python 2,后来在 Python 3 中恢复),并且模块运算符仍然可能会带来惊喜(带有负数)

© www.soinside.com 2019 - 2024. All rights reserved.