假设我有以下数据框:
elements = [1,1,1,1,1,2,3,4,5]
df = pd.DataFrame({'elements': elements})
df.set_index(['elements'])
print df
elements
0 1
1 1
2 1
3 1
4 1
5 2
6 3
我有一个列表[1, 1, 2, 3]
,我想要一个包含这4个元素的数据帧的子集,例如:
elements
0 1
1 1
5 2
6 3
我已经能够通过构建一个计算数组中项目出现次数的dict并通过附加初始数据的子部分来构建新的数据帧来处理它。
您是否了解一些数据框方法以帮助我找到更优雅的解决方案?
在@jezrael评论之后:我必须补充一点,我需要跟踪初始索引(以df为单位)。
我们可以看到df(第一个数据帧)作为资源的存储库,我需要跟踪哪些行/索引归属:
用例是:在df中的元素中给我两个1,一个2和一个3.我会坚持我的行0和1为1,第4行为2,第5行为3。 / p>
答案 0 :(得分:2)
当且仅当您的Series
和list
已排序(否则,请参阅下文),您可以执行以下操作:
L = [1, 1, 2, 3]
df[df.elements.apply(lambda x: x == L.pop(0) if x in L else False)]
elements
0 1
1 1
5 2
6 3
list.pop(i)
返回并删除list
处索引i
处的值。由于elements
和L
都已排序,因此弹出子集列表i==0
的第一个元素(L
)将始终出现在{{{ 1}}。
因此,在elements
的{{1}}的每次迭代中,lambda
将成为:
elements
正如您所看到的,您的列表最后是空的,所以如果它出现问题,您可以事先复制它。或者,您实际上在刚刚创建的新数据框中拥有该信息!
如果未对L
进行排序,请创建一个排序副本,在该副本上应用与上面相同的lambda函数,但它的输出将用作原始数据帧的索引(使用值为True的索引) ):
| element | L | Output |
|=========|==============|===========|
| 1 | [1, 1, 2, 3] | True |
| 1 | [1, 2, 3] | True |
| 1 | [2, 3] | False |
| 1 | [2, 3] | False |
| 1 | [2, 3] | False |
| 2 | [2, 3] | True |
| 3 | [3] | True |
| 4 | [] | False |
| 5 | [] | False |
HTH
答案 1 :(得分:0)
merge
的新列可以通过GroupBy.cumcount
提取{/ 3>}来提取。
L = [1,1,2,3]
df1 = pd.DataFrame({'elements':L})
df['g'] = df.groupby('elements')['elements'].cumcount()
df1['g'] = df1.groupby('elements')['elements'].cumcount()
print (df)
elements g
0 1 0
1 1 1
2 1 2
3 1 3
4 1 4
5 2 0
6 3 0
7 4 0
8 5 0
print (df1)
elements g
0 1 0
1 1 1
2 2 0
3 3 0
print (pd.merge(df,df1, on=['elements', 'g']))
elements g
0 1 0
1 1 1
2 2 0
3 3 0
print (pd.merge(df.reset_index(),df1, on=['elements', 'g'])
.drop('g', axis=1)
.set_index('index')
.rename_axis(None))
elements
0 1
1 1
5 2
6 3