我正在尝试在Pandas DataFrame中的一行中重新分配值。
import pandas as pd
import numpy as np
这是DataFrame:
test_df = pd.DataFrame({'range_total' : [3000,3000,3000,3000,3000,3000,0,2000,2000,1000,1000,1000,1000,1000,1000],
'high_boundary' : [6,6,6,6,6,6,7,9,9,15,15,15,15,15,15],
'dist_num' : [1197, 142, 142, 1197, 159, 159, 0, 1000, 1000, 398, 50, 50, 398, 50, 50],
'round_num_sum' : [2996, 2996, 2996, 2996, 2996, 2996, 0, 2000, 2000, 996, 996, 996, 996, 996, 996]})
在我的代码中,我为high_boundary
的每个值对DataFrame进行了子集,并找到与test_df
的最大值对应的dist_num
的索引(如果绑定则选择第一个值) )。对于此示例,我将索引设置为:
sub_idx = 0
我可以使用此(和其他类似版本)代码访问该值:
test_df.ix[(test_df.high_boundary == 6), "dist_num"][sub_idx]
返回:
1197
但是分配新值失败:
test_df.ix[(test_df.high_boundary == 6), "dist_num"][sub_idx] = 42
test_df.ix[(test_df.high_boundary == 6), "dist_num"][sub_idx]
仍然会返回:
1197
可是:
test_df.ix[(test_df.high_boundary == 6), "dist_num"] = 42
test_df.ix[(test_df.high_boundary == 6), "dist_num"]
返回:
0 42
1 42
2 42
3 42
4 42
5 42
Name: dist_num, dtype: int64
我感谢任何帮助。这是我的第一篇文章,因为直到现在我总能找到我所需要的东西。我使用的是版本0.14.0。
答案 0 :(得分:0)
有时您可以获得(部分)原始数据框test_df
的副本。
特别是如果您使用[...][...]
所以你在副本中更改了一个值,而不是在原始test_df
试试这个例子:
test_df["dist_num"].ix(test_df.high_boundary == 6)[sub_idx] = 0
你应该得到预期的结果。
答案 1 :(得分:0)
过去有过类似的问题。建议你通过
的例子来工作http://pandas.pydata.org/pandas-docs/stable/indexing.html
特别是该部分 http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy会帮助你。
编辑解释说,如果你使用df [] []构造进行链切片,你经常会切换到第1个系列然后切换到值。 pandas跟踪原始过滤器以允许您回写切片是不可行的。
简短回答尝试使用单个运算符(如“.loc”)来执行您要分配的选择。
答案 2 :(得分:0)
几年后重新访问此代码时,我发现上面发布的解决方案现在提供了一个错误(使用Pandas版本0.20.1和Python 2.7.13):
TypeError: 'Series' objects are mutable, thus they cannot be hashed
。如果其他人有这个问题,我在下面添加了一个解决方案。
要更新pd.DataFrame
子集的单个元素,找到子集中的索引值,然后使用与所需行对应的索引来选择要更新的元素
sub_idx = 0
indices = test_df.loc[test_df.high_boundary == 6,"dist_num"].index
print(test_df.loc[indices[sub_idx],"dist_num"])
# 1197
test_df.loc[indices[sub_idx],"dist_num"] = 0
print(test_df.loc[indices[sub_idx],"dist_num"])
# 0