Pandas 通过三列的组合筛选n个第一个值

Pandas 通过三列的组合筛选n个第一个值,pandas,Pandas,我有一个4列的排序数据框,如下所示。我正在尝试过滤我的数据帧,以便对于(Var1,Var2,Var3)的每个组合,我为Var4保留2个第一个disctint值。 例如,我在数据帧中的(Var1,Var2,Var3)的第一个组合是(A,B,C)。此组合的前两个不同值是值_1和值_2。 (Var1,Var2,Var3)的第二个组合是(A,C,C)。对于这个组合,我只有一种类型的值,它是value_14。 等等 输入: Var1 Var2 Var3 Var4 1 A

我有一个4列的排序数据框,如下所示。我正在尝试过滤我的数据帧,以便对于(Var1,Var2,Var3)的每个组合,我为Var4保留2个第一个disctint值。 例如,我在数据帧中的(Var1,Var2,Var3)的第一个组合是(A,B,C)。此组合的前两个不同值是值_1和值_2。 (Var1,Var2,Var3)的第二个组合是(A,C,C)。对于这个组合,我只有一种类型的值,它是value_14。 等等

输入:

       Var1  Var2  Var3  Var4
    1     A    B      C  value_1
    2     A    B      C  value_1
    3     A    B      C  value_1
    4     A    B      C  value_1
    5     A    B      C  value_2
    6     A    B      C  value_2
    7     A    B      C  value_3
    8     A    B      C  value_3
    9     A    B      C  value_3
    10    A    B      C  value_4
   11     A    C      C  value_14
   12     A    C      C  value_14
   13     A    C      C  value_14
   14     A    C      C  value_14
   15     B    B      C  value_21
   16     B    B      C  value_21
   17     B    B      C  value_32
   18     B    B      C  value_32
   19     B    B      C  value_33
   20     B    B      C  value_43
输出:

       Var1  Var2  Var3  Var4
    1     A    B      C  value_1
    2     A    B      C  value_1
    3     A    B      C  value_1
    4     A    B      C  value_1
    5     A    B      C  value_2
    6     A    B      C  value_2
   11     A    C      C  value_14
   12     A    C      C  value_14
   13     A    C      C  value_14
   14     A    C      C  value_14
   15     B    B      C  value_21
   16     B    B      C  value_21
   17     B    B      C  value_32
   18     B    B      C  value_32
   Var1 Var2 Var3      Var4
0     A    B    C   value_1
1     A    B    C   value_1
2     A    B    C   value_1
3     A    B    C   value_1
4     A    B    C   value_2
5     A    B    C   value_2
6     A    C    C  value_14
7     A    C    C  value_14
8     A    C    C  value_14
9     A    C    C  value_14
10    B    B    C  value_21
11    B    B    C  value_21
12    B    B    C  value_32
13    B    B    C  value_32
注意,我的数据帧有500万行。到目前为止,我已经找到了一个使用循环的解决方案,但这几乎需要一个小时。

我们可以使用

df[df.groupby(['Var1','Var2','Var3'])['Var4'].apply(lambda x : x.groupby(x).ngroup()<2)]

Out[106]: 
   Var1 Var2 Var3      Var4
1     A    B    C   value_1
2     A    B    C   value_1
3     A    B    C   value_1
4     A    B    C   value_1
5     A    B    C   value_2
6     A    B    C   value_2
11    A    C    C  value_14
12    A    C    C  value_14
13    A    C    C  value_14
14    A    C    C  value_14
15    B    B    C  value_21
16    B    B    C  value_21
17    B    B    C  value_32
18    B    B    C  value_32

df[df.groupby(['Var1','Var2','Var3'])['Var4'].apply(lambda x:x.groupby(x).ngroup()
ngroup
标记组,然后通过减去最小值确保每个组从0开始。然后是一个简单的掩码

s = df.groupby([*df], sort=False).ngroup()  #sort = False keeps ordering of Val4
s = s - s.groupby([df.Var1, df.Var2, df.Var3]).transform('min')

df[s.le(1)]

让我们使用这个方法:

df.drop_duplicates(['Var1','Var2','Var3','Var4'])\
  .groupby(['Var1','Var2','Var3']).head(2)\
  .merge(df, on=['Var1','Var2','Var3','Var4'])
输出:

       Var1  Var2  Var3  Var4
    1     A    B      C  value_1
    2     A    B      C  value_1
    3     A    B      C  value_1
    4     A    B      C  value_1
    5     A    B      C  value_2
    6     A    B      C  value_2
   11     A    C      C  value_14
   12     A    C      C  value_14
   13     A    C      C  value_14
   14     A    C      C  value_14
   15     B    B      C  value_21
   16     B    B      C  value_21
   17     B    B      C  value_32
   18     B    B      C  value_32
   Var1 Var2 Var3      Var4
0     A    B    C   value_1
1     A    B    C   value_1
2     A    B    C   value_1
3     A    B    C   value_1
4     A    B    C   value_2
5     A    B    C   value_2
6     A    C    C  value_14
7     A    C    C  value_14
8     A    C    C  value_14
9     A    C    C  value_14
10    B    B    C  value_21
11    B    B    C  value_21
12    B    B    C  value_32
13    B    B    C  value_32

不确定这对于您的数据集是否会更快。