根据多列的值删除重复的所有行

时间:2014-08-22 22:19:20

标签: python pandas group-by duplicates dataframe

我有一个包含多列和多行(200k)的大型数据帧。我按组变量排序行,每个组可以有一个或多个条目。每组的其他列应该具有相同的值,但在某些情况下它们不会。它看起来像这样:

group   name    age    color
1       Anton   50     orange
1       Anton   21     red
1       Anton   21     red
2       Martin  78     black
2       Martin  78     blue
3       Maria   25     red
3       Maria   29     pink
4       Jake    33     blue

如果组的所有行的年龄或颜色不相同,我想要删除组的所有条目。(表示观察错误)但是如果所有列都具有相同的值,我想保留重复的条目。 所以我希望的输出是:

group   name    age    color   
2       Martin  78     black
2       Martin  78     blue  
4       Jake    33     blue

在类似的情况下,我正在使用这个功能,它的工作速度非常快: df = df.groupby('group')。filter(lambda x:x.count()== 1)

然而,这不允许我检查列的值(年龄,颜色)。 我一直在玩groupby功能,但似乎无法掌握它。

/ e:我刚刚意识到我在我的问题中错过了一个重要条件:如果一个或多个SPECIFIC列具有重复值,我只想删除观察结果。但是其他列可能不同。在上面的例子中,让我说我不在乎组内的颜色是否有差异,但只想检查年龄是否有不同的值。(我编辑的例子反映了这一点)。我的实际情况更为一般并包含更多列,所以我想要例如在删除观察时检查几列并忽略其他列。

2 个答案:

答案 0 :(得分:2)

虽然@ ismax的答案可行,但您可以使用与.count()解决方案类似的模式,但首先删除重复项。

In [229]: In [179]: df.groupby('group').filter(lambda x: len(x.drop_duplicates(subset=['age'])) == 1)
Out[229]: 
   group    name  age  color
3      2  Martin   78  black
4      2  Martin   78   blue
7      4    Jake   33   blue

答案 1 :(得分:0)

您可以使用计数器字典解决此问题。

from collections import defaultdict, Counter

N = int(input())#read number of tuples
mapGroupAge = defaultdict(Counter)#a dict of counters to count 
                                  #the repetitions by group

for _ in range(N):
    # read tuples (from standard input in this example)
    group,name,age,color = input().split()
    #build the map (dict) indexed by the groups i.e. a key is a pair (group,name)
    mapGroupAge[(group,name)][(age,color)] += 1

for (group,name), counter in mapGroupAge.items():
    # if all ages and colors for the same group are the same
    if(len(counter)==1):
        age,color = list(counter.keys())[0]
        # print all the repetitions
        for _ in range(counter[(age,color)]):
            print(group, name, age,color)

您可以通过执行它并在标准输入中粘贴以下行来测试上面的代码:

8
1       Anton   50     orange
1       Anton   21     red
1       Anton   21     red
2       Martin  78     blue
2       Martin  78     blue
3       Maria   25     red
3       Maria   25     pink
4       Jake    33     blue

如您所愿,执行结果为:

2 Martin 78 blue
2 Martin 78 blue
4 Jake 33 blue
相关问题