2017-02-22 11 views
0

У меня есть файлы данных, которые содержат столбец «имя, время, данные», я хотел бы найти дублированные данные (имя, время должно точно совпадать и данные (если любые двоичные данные »1 "совпадают независимо от позиции) Например, данные ниже:. есть ли доступна функция может сделать этоПоиск дублированных данных с использованием Python

Например:

name,time,data 
tg,0x34,1111 
ab,0x54,1011 
k,0x34,0100 
c,0x34,0001 
e,0x34,0000 
d, 0x34,1111 

дублируется результат:

tg,0x34,1111 
k,0x34,0100 
c,0x34,0001 
d, 0x34,1111 
+0

Как выведенный результат является допустимым? –

+0

Я в замешательстве. Итак, мы удаляем любые строки, которые не имеют дубликата в столбце 'time'? Вообще, для такого рода манипуляций с данными, я бы предложил посмотреть на «панды». – spicypumpkin

+0

Вам нужны все строки, где только второй столбец одинаковый? – wwii

ответ

1

Это похоже на проблему сортировки, группировки, сравнения. Не совсем уверен, почему, но я выбрал класс, который имеет методы, необходимые для сортировки, группировки и сравнения. ... Python 2.7 код:

Setup;

import io, collections, operator, csv 

s = '''name,time,data 
tg,0x34,1111 
ab,0x54,1011 
k,0x34,0100 
c,0x34,0001 
e,0x34,0000 
d,0x34,1111''' 

# for file emulation 
f = io.BytesIO(s) 

Класс для провести инфо и работа с инструментами Python

class Thing(object): 
    def __init__(self, name = None, time = None, data = None): 
     self. name = name 
     self.time = time 
     self.data = data 
    def __eq__(self, other): 
     'For comparison' 
     equal = self.time == other.time 
     # equal if there is a one in both things at the same bit position 
     equal = equal and bool(int(self.data, base = 2) & 
           int(other.data, base = 2)) 
     return equal 
    def __lt__(self, other): 
     'For sorting' 
     return self.time < other.time 
    def __str__(self): 
     return '({}, {}, {})'.format(self.name, self.time, self.data) 
    def __repr__(self): 
     return '({}, {}, {})'.format(self.name, self.time, self.data) 

Используйте модуль CSV, чтобы сделать список Thing-х и сортирует их (time):

reader = csv.DictReader(f) 
things = [Thing(**row) for row in reader] 
things.sort() 

Используйте itertools.groupby и itertools.combination, чтобы сравнить вещи с одинаковыми time , Поместите вещи, которые равны в наборе.

results = set() 
for key, group in itertools.groupby(things, key = operator.attrgetter('time')): 
    print key 
    for a, b in itertools.combinations(group, 2): 
     if a == b: 
      print '\t{} is duplicate of {}'.format(a, b) 
      results.add(a) 
      results.add(b) 

Это приводит к

>>> 
0x34 
    (tg, 0x34, 1111) is duplicate of (k, 0x34, 0100) 
    (tg, 0x34, 1111) is duplicate of (c, 0x34, 0001) 
    (tg, 0x34, 1111) is duplicate of (d, 0x34, 1111) 
    (k, 0x34, 0100) is duplicate of (d, 0x34, 1111) 
    (c, 0x34, 0001) is duplicate of (d, 0x34, 1111) 
0x54 
>>> results 
set([(tg, 0x34, 1111), (c, 0x34, 0001), (d, 0x34, 1111), (k, 0x34, 0100)]) 
>>> 

Не уверен, что, если я понял спецификации - Нижеперечисленные набора данных производит ноль дубликатов:

s = '''name,time,data 
tg,0x34,0010 
ab,0x54,1011 
k,0x34,0100 
c,0x34,0001 
e,0x34,0000 
d,0x34,1000''' 

You вероятно, хотят, чтобы дубликаты были раздельными, поэтому держите их в словаре, используя время в качестве ключа.

results = collections.defaultdict(set) 
for key, group in itertools.groupby(things, key = operator.attrgetter('time')): 
    print key 
    for a, b in itertools.combinations(group, 2): 
     if a == b: 
      print '\t{} is duplicate of {}'.format(a, b) 
      results[key].update((a,b)) 
+0

, это именно то, что я ищу, спасибо за отличный пример с приведенным выше кодом! Сегодня я узнал что-то новое: функции itertools.combination. – user37970

+0

@ user37970 - не стесняйтесь принимать ответ. – wwii

 Смежные вопросы

  • Нет связанных вопросов^_^