【问题标题】:Creating and modifying an empty Pandas DataFrame results in unpredictable behavior创建和修改空的 Pandas DataFrame 会导致不可预测的行为
【发布时间】:2014-03-26 01:39:20
【问题描述】:

我试图理解为什么我的代码(它初始化然后修改 Pandas DataFrame 中的一个新列)表现异常。我的代码如下:

pos = df['sign'] == 'Pos'
neg = df['sign'] == 'Neg'
df['signed_val'] = 0
df['signed_val'][pos] =  df['abs_val'][pos]
df['signed_val'][neg] = -df['abs_val'][neg]
df['pos_part'] = (df['abs_val']+df['signed_val'])/2

这里,df 是一个现有的 DataFrame,其中包含标记为“abs_val”和“sign”的列。我的目标是创建一个新列,其中包含一个额外的行“signed_val”,其中包含“abs_val”的签名版本。

当我运行此代码时,会发生两种情况之一。首先,如果我将整个代码块复制并粘贴到我的 python 解释器中,df['signed_val'] 将被全零填充。或者,如果我一次将一行复制并粘贴到我的 python 解释器中,df['signed_val'] 似乎给出了df['abs_val'] 的签名版本。

显然,这种行为是不可接受的。我在这里做错了什么,还是这是一个错误?

更新

当最后一行打印出df['abs_val'] 的签名版本时,以下代码似乎可以正常运行:

pos = df['sign'] == 'Pos'
neg = df['sign'] == 'Neg'
df['signed_val'] = 0
df['signed_val'][pos] =  df['abs_val'][pos]
df['signed_val'][neg] = -df['abs_val'][neg]
df['signed_val']

但是,一旦运行另一个命令,df['signed_val'] 就会打印出一个零向量。以下第三个代码块可能会按预期运行,尽管我没有对其进行广泛测试:

pos = df['sign'] == 'Pos'
neg = df['sign'] == 'Neg'
df['signed_val'] = numpy.nan
df['signed_val'][pos] =  df['abs_val'][pos]
df['signed_val'][neg] = -df['abs_val'][neg]
df['pos_part'] = (df['abs_val']+df['signed_val'])/2

不过,第一个代码块发生了什么?

我使用的是 pandas 0.13.1 版和 numpy 1.8.0 版。

【问题讨论】:

    标签: python pandas


    【解决方案1】:

    您正在执行链式分配,请参见此处:http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy

    在单个 dtyped 框架上,这将始终有效;一般来说,在多类型框架上不会。

    改为使用索引器loc/ix 来可靠地设置值。

    【讨论】:

    • 我很好奇我看不出第一个和第二个代码块之间的区别,为什么它们的行为不同?我错过了什么吗?
    • 我的意思是代码 df['signed_val'][pos] = df['abs_val'][pos] 即使在第一个代码块中也应该工作,因为 df['signed_val'] 是引用,而不是副本。为什么OP说它不起作用?第一个和第二个代码块之间似乎没有什么不同(除了代码块 1 中的最后一行)。
    • 您错过了重点,它在单个 dtyped 案例中工作(很明显这不是单个 dtyped 案例)。这可以复制;这取决于 numpy 是否创建视图。阅读链式索引部分。它不是 python 案例中的参考。这通过熊猫__getitem__。这就是为什么链式索引很隐蔽并且永远不应该使用的原因。 (也不清楚这里使用的是哪个版本的 pandas;更新的版本确实会在 一些 类似的情况下提供警告)。
    猜你喜欢
    • 2013-02-04
    • 2021-07-27
    • 1970-01-01
    • 1970-01-01
    • 2018-12-05
    • 2013-06-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多