如何使用Pandas从groupby对象返回数据帧?这里的目的是读取CSV并使用randIP()返回的值替换IP地址列中的每个IP地址。我希望通过分组来保持之后整个混淆数据帧的一致性(每个真实IP映射到新的随机IP)。
我尝试了很多方法,但这似乎是最成功的。 self.df2正在打印为pandas.core.grouby.SeriesGroupBy对象。
def __init__(self, filename):
self.df = pd.read_csv(filename)
self.grouped = self.df.groupby('IP Address')
self.df.reset_index(drop=True, inplace=True)
for i, k in self.grouped:
r = randIP()
k['IP Address'] = k['IP Address'].apply(lambda x: x.replace(x, r))
self.df2 = self.grouped
print(self.df2['IP Address'])
答案 0 :(得分:0)
最好不要尝试从分组操作中修改DataFrame。相反,使用分组操作创建新IP,然后使用map
将旧IP映射到新IP,然后(如果需要)将新IP分配回新IP数据帧:
def randomIP():
return ".".join(str(np.random.randint(0, 255) for it in xrange(4)))
>>> d = pandas.DataFrame({'IP': ['1.2.3.4', '5.6.7.8', '1.2.3.4', '5.6.7.8', '9.10.11.12', '13.14.15.16'], 'Other': ['blah']*6})
>>> d
IP Other
0 1.2.3.4 blah
1 5.6.7.8 blah
2 1.2.3.4 blah
3 5.6.7.8 blah
4 9.10.11.12 blah
5 13.14.15.16 blah
将groupby
与apply
一起使用会为您提供旧版IP到新版IP的系列映射:
>>> d.groupby('IP').apply(lambda g: randomIP())
IP
1.2.3.4 4.183.193.46
13.14.15.16 186.124.189.188
5.6.7.8 152.24.105.42
9.10.11.12 188.140.91.209
在旧IP列上使用map
并传递此新系列会将旧IP映射到新IP:
>>> d.IP.map(d.groupby('IP').apply(lambda g: randomIP()))
0 47.227.125.190
1 164.86.98.48
2 47.227.125.190
3 164.86.98.48
4 44.150.90.127
5 71.111.59.115
Name: IP, dtype: object
如果您想将它们重新分配回DataFrame列,您可以这样做:
>>> d['IP'] = d.IP.map(d.groupby('IP').apply(lambda g: randomIP()))
>>> d
IP Other
0 238.227.204.61 blah
1 13.201.160.89 blah
2 238.227.204.61 blah
3 13.201.160.89 blah
4 69.33.243.79 blah
5 164.120.13.218 blah
我认为最后一个是您正在寻找的一体化解决方案。 (在这些示例中,随机IP每次都不同,因为我在示例的每个部分再次调用randomIP
。)