2014-11-04 166 views
2

我发誓我首先搜索了它,并发现了很多“可以工作 - 如果适应”,但没有什么帮助。我有什么是元组的形式列表:Python3根据索引的值中的一个值唯一化元组列表

[('', '[email protected]'), ('Andrea', '[email protected]'), ('Your Book', '[email protected]'), ..] 

在这种情况下,这是一个元组列表,有一个“名称”作为第一个值,而“电子邮件”作为第二个价值,所有指标。并且列表没有以任何特定的方式排序(还)。

我需要的是一个干净的和可以理解的(我不一定要找的俏皮话,我甚至不能读取)的方式来产生“uniquified”列表中,但这些规则/警告:

  • 只有在找到元组第二个值的副本(在这种情况下,它恰好是电子邮件地址,并且它将是“[email protected]”)时,才会删除元组。
  • 不要消除所有重复元组的实例。我需要保留一个,并且要保留的那个应该是第一个对象的len()最多的元组。 (在这种情况下,重复的元组,它只会保留元组(“你的书”,“[email protected]”)

在这个最小例如最后的结果将是:

[('Andrea', '[email protected]'), ('Your Book', '[email protected]'), ..] 

,因为我知道如何排序未排序的元组的列表不要紧,如果输出未下令或排序感谢

回答

2

方法1:收集所有的名字

如果我们想最易懂的版本,不灵巧,可能像

pairs = [('', '[email protected]'), ('Andrea', '[email protected]'), ('Your Book', '[email protected]')] 

data = {} 
for name, email in pairs: 
    if email not in data: 
     data[email] = [] 
    data[email].append(name) 

output = [(email, max(data[email], key=len)) for email in data] 

会工作。这将问题分解为两部分:建立一个以电子邮件地址为关键字和可能的名称列表作为值的字典;并循环所有的电子邮件地址,并获得最长的名字。

第一部分可以使用setdefault(例如,

for name, email in pairs: 
    data.setdefault(email, []).append(name) 

但并非所有人都熟悉这一点。


方法2:排序,使独特的

或者,我们可以通过电子邮件,姓名长度进行排序,然后建立从一本字典,将只保留看到的最后一个键/值对:

>>> pairs.sort(key=lambda x: (x[1], len(x[0]))) 
>>> data = {v: k for k,v in pairs} 
>>> [(v,k) for k,v in data.items()] 
[('Andrea', '[email protected]'), ('Your Book', '[email protected]')] 
+0

感谢您解释这两种方法,它可以想象试图抽象自己的问题。我正在执行#2,但是这是做了哪些工作,谢谢:) – newyuppie 2014-11-04 04:32:26

0

可能做到这一点最简单的方法是使用一组这样的:

L = [('', '[email protected]'), ('Andrea', '[email protected]'), ('Your Book', '[email protected]'), ..] 

emails = set() 

result_L = [] 

for item in L: 
    if item[1] in emails: 
     # this email address is already seen 
     continue 

    result_L += [item] 
    emails.add(item[1]) 

不过,如果你想保留的最后一个项目,你可以使用这个(在最后,你可能想扭转result_L):

for i in reversed(L): 
    # ... 

还有很多其他的方法可以做到这一点,太。例如,请考虑使用dict

result_dict = {} 

for item in L: 
    result_dict[item[1]] = item[0] 

result_L = [(y, x) for (x, y) in result_dict.items()] 
1

你可以建立一个使用第二个条目为你的关键一本字典。字典具有不含任何重复的特性。如果您的第一个元素的长度构建字典之前进行排序,它会为你提供你所追求的:

your_list_sorted = sorted(your_list, key=lambda x: len(x[0])) 
out = dict((v, k) for k, v in your_list_sorted) 

如果你需要以列表的形式您的输出,你可以做out_list = list(out.items())得到它。

+0

我最终使用了@ DSM提出的类似方法,它使用了Dictionary。但在你的情况下,它扭转了它,所以这是一个额外的步骤。但你的答案显然也有效,所以+1。 – newyuppie 2014-11-04 04:34:10

相关问题