python - 为什么在我遍历 pandas DataFrame 后这个函数 "take"不起作用?

标签 python pandas

我有一个带有时间戳的温度和风速值的 DataFrame,以及一个将这些值转换为“风寒”的函数。我正在使用 iterrows 在每一行上运行函数,并希望得到一个带有漂亮的“Wind Chill”列的 DataFrame。

然而,虽然它似乎在进行过程中有效,并且实际上至少“有效”过一次,但我似乎无法始终如一地复制它。总的来说,我觉得我在 DataFrames 的结构中缺少一些东西,但我希望有人能提供帮助。

In [28]: bigdf.head()
Out[28]: 


                           Day  Temperature  Wind Speed  Year
2003-03-01 06:00:00-05:00  1    30.27        5.27        2003
2003-03-01 07:00:00-05:00  1    30.21        4.83        2003
2003-03-01 08:00:00-05:00  1    31.81        6.09        2003
2003-03-01 09:00:00-05:00  1    34.04        6.61        2003
2003-03-01 10:00:00-05:00  1    35.31        6.97        2003

因此,我将“Wind Chill”列添加到 bigdf 并使用 NaN 进行预填充。

In [29]: bigdf['Wind Chill'] = NaN

然后我尝试遍历行,添加实际的 Wind Chills。

In [30]: for row_index, row in bigdf[:5].iterrows():
    ...:     row['Wind Chill'] = windchill(row['Temperature'], row['Wind Speed'])
    ...:     print row['Wind Chill']
    ...:
24.7945889994
25.1365267133
25.934114012
28.2194307516
29.5051046953

正如您所说,新值出现 将应用于“Wind Chill”列。这是 windchill 函数,以防万一:

def windchill(temp, wind):
    if temp>50 or wind<=3:
        return temp
    else:
        return 35.74 + 0.6215*temp - 35.75*wind**0.16 + 0.4275*temp*wind**0.16

但是,当我再次查看 DataFrame 时,NaN 仍然存在:

In [31]: bigdf.head()
Out[31]: 

                           Day  Temperature  Wind Speed  Year  Wind Chill
2003-03-01 06:00:00-05:00  1    30.27        5.27        2003  NaN
2003-03-01 07:00:00-05:00  1    30.21        4.83        2003  NaN
2003-03-01 08:00:00-05:00  1    31.81        6.09        2003  NaN
2003-03-01 09:00:00-05:00  1    34.04        6.61        2003  NaN
2003-03-01 10:00:00-05:00  1    35.31        6.97        2003  NaN

更奇怪的是,它已经工作了一两次,而且我无法说出我做了什么不同。

我必须承认我不是特别熟悉 pandas 的内部工作原理,并且对索引等感到困惑,所以我觉得我可能在这里遗漏了一些非常基本的东西(或者以困难的方式做到这一点)。

谢谢!

最佳答案

您可以使用 apply这样做:

In [11]: df.apply(lambda row: windchill(row['Temperature'], row['Wind Speed']),
                 axis=1)
Out[11]:
2003-03-01 06:00:00-05:00    24.794589
2003-03-01 07:00:00-05:00    25.136527
2003-03-01 08:00:00-05:00    25.934114
2003-03-01 09:00:00-05:00    28.219431
2003-03-01 10:00:00-05:00    29.505105

In [12]: df['Wind Chill'] = df.apply(lambda row: windchill(row['Temperature'], row['Wind Speed']),
                                    axis=1)

In [13]: df
Out[13]:
                           Day  Temperature  Wind Speed  Year  Wind Chill
2003-03-01 06:00:00-05:00    1        30.27        5.27  2003   24.794589
2003-03-01 07:00:00-05:00    1        30.21        4.83  2003   25.136527
2003-03-01 08:00:00-05:00    1        31.81        6.09  2003   25.934114
2003-03-01 09:00:00-05:00    1        34.04        6.61  2003   28.219431
2003-03-01 10:00:00-05:00    1        35.31        6.97  2003   29.505105

.

为了进一步说明您混淆的原因,我认为这是因为行变量是 copies rather than views。 df 的,因此更改不会传播:

In [21]: for _, row in df.iterrows(): row['Day'] = 2

我们看到它正在成功地对副本进行更改变量:

In [22]: row
Out[22]:
Day               2.00
Temperature      35.31
Wind Speed        6.97
Year           2003.00
Name: 2003-03-01 10:00:00-05:00

但是他们没有更新到 DataFrame:

In [23]: df
Out[23]:
                           Day  Temperature  Wind Speed  Year
2003-03-01 06:00:00-05:00    1        30.27        5.27  2003
2003-03-01 07:00:00-05:00    1        30.21        4.83  2003
2003-03-01 08:00:00-05:00    1        31.81        6.09  2003
2003-03-01 09:00:00-05:00    1        34.04        6.61  2003
2003-03-01 10:00:00-05:00    1        35.31        6.97  2003

以下也保持 df 不变:

In [24]: row = df.ix[0]  # also a copy

In [25]: row['Day'] = 2

而如果我们确实进行查看:(我们将看到一个更改 df。)

In [26]: row = df.ix[2:3]  # this one's a view

In [27]: row['Day'] = 3

参见 Returning a view versus a copy (in the docs) .

关于python - 为什么在我遍历 pandas DataFrame 后这个函数 "take"不起作用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15972264/

相关文章:

Python 带条件断言

python - 我可以为重置索引指定名称吗?

pandas - 如何更改 DataFrame 中堆积区域图的填充颜色?

python - 如何删除 Pandas 列中特殊字符前面的部分字符串?

c++ - Python C API 和 C++ 函数

python - Python 中的多个套接字/重用/关闭套接字? _socketobject 错误

python - 网络抓取(获取表格时出现问题)

python - 以更有效的方式过滤数据帧

Python:SettingWithCopyWarning:试图在 DataFrame 的切片副本上设置一个值

python - 指定名称时,Pandas read_csv 不会引发错误行的异常