Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/282.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 基于多列的值删除副本的所有行_Python_Pandas_Group By_Duplicates_Dataframe - Fatal编程技术网

Python 基于多列的值删除副本的所有行

Python 基于多列的值删除副本的所有行,python,pandas,group-by,duplicates,dataframe,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

我有一个包含多列和多行的大型数据框(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:我刚刚意识到我的问题中遗漏了一个重要条件:我只想删除观察值,如果一个或多个特定列有重复的值。但是,其他列可以不同。在上面的示例中,假设我不关心组内颜色之间是否存在差异,但只想检查年龄是否具有不同的值。(我编辑示例以反映这一点)。我的实际案例更一般,包含更多列,因此,我想检查一些列,在删除观察值时忽略其他列。

您可以使用一组计数器来解决这个问题

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

虽然@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

这和我想要的差不多。然而,我才意识到我的问题不够精确。我编辑它是为了更恰当地反映我的具体情况。@cover51-请参见编辑,只需将列传递给
子集
参数即可。