使用iloc从另一个查询数据帧

时间:2019-06-16 06:40:19

标签: pandas

具有一个具有用于查找的位置和列的数据框,如下所示:

import pandas as pd
import numpy as np

i = ['dog', 'cat', 'bird', 'donkey'] * 100000

df1 = pd.DataFrame(np.random.randint(1, high=380, size=len(i)), 
                  ['cat', 'bird', 'donkey', 'dog'] * 100000).reset_index()
df1.columns = ['animal', 'locn']
df1.head()

要查看的数据帧如下:

df = pd.DataFrame(np.random.randn(len(i), 2), index=i,
     columns=list('AB')).rename_axis('animal').sort_index(0).reset_index()
df

正在为df1中的每条记录寻找一种更快的方式来为列分配B值。

df1.assign(val=[df[df.animal == a].iloc[b].B for a, b in zip(df1.animal, df1['locn'])])

...非常慢。

1 个答案:

答案 0 :(得分:2)

animal列的计数器使用GroupBy.cumcount用于位置,因此可以与左联接合并使用:

df['locn'] = df.groupby('animal').cumcount()
df1['new'] = df1.merge(df.reset_index(), on=['animal','locn'], how='left')['B']

在较小的数据框中验证:

np.random.seed(2019)
i = ['dog', 'cat', 'bird', 'donkey'] *  100

df1 = pd.DataFrame(np.random.randint(1, high=10, size=len(i)), 
                  ['cat', 'bird', 'donkey', 'dog'] * 100).reset_index()
df1.columns = ['animal', 'locn']
print (df1)

df = pd.DataFrame(np.random.randn(len(i), 2), index=i,
     columns=list('AB')).rename_axis('animal').sort_index(0).reset_index()

df1 = df1.assign(val=[df[df.animal == a].iloc[b].B for a, b in zip(df1.animal, df1['locn'])])

df['locn'] = df.groupby('animal').cumcount()
df1['new'] = df1.merge(df.reset_index(), on=['animal','locn'], how='left')['B']

locn = df.groupby('animal').cumcount()
df1 = df1.assign(new1 = df1.merge(df.reset_index().assign(locn = locn), 
                                  on=['animal','locn'], how='left')['B'])

print (df1.head(10))
   animal  locn       val       new      new1
0     cat     9 -0.535465 -0.535465 -0.535465
1    bird     3  0.296240  0.296240  0.296240
2  donkey     6  0.222638  0.222638  0.222638
3     dog     9  1.115175  1.115175  1.115175
4     cat     7  0.608889  0.608889  0.608889
5    bird     9 -0.025648 -0.025648 -0.025648
6  donkey     1  0.324736  0.324736  0.324736
7     dog     1  0.533579  0.533579  0.533579
8     cat     8 -1.818238 -1.818238 -1.818238
9    bird     9 -0.025648 -0.025648 -0.025648