代码之家  ›  专栏  ›  技术社区  ›  Arkistarvh Kltzuonstev

基于元组的第二项从元组列表中删除列表项

  •  0
  • Arkistarvh Kltzuonstev  · 技术社区  · 6 年前

    我有一个元组列表:

    ap = [('unknown', (81, 717, 236, 562)), ('unknown', (558, 1033, 825, 765)), ('unknown', (96, 1142, 225, 1013)), ('Jenny', (558, 1033, 825, 765)), ('unknown', (477, 1233, 632, 1078)), ('unknown', (741, 1199, 868, 1070)), ('Garry', (53, 282, 182, 153)), ('Sam', (477, 1233, 632, 1078)), ('Chen', (593, 283, 779, 97)), ('Steve', (741, 1199, 868, 1070)), ('unknown', (53, 282, 182, 153)), ('Harry', (81, 717, 236, 562)), ('unknown', (593, 283, 779, 97))]
    

    ap = [('Harry',(81, 717, 236, 562)), ('Jenny', (558, 1033, 825, 765)), ('unknown', (96, 1142, 225, 1013)), ('Sam', (477, 1233, 632, 1078)), ('Steve', (741, 1199, 868, 1070)), ('Garry', (53, 282, 182, 153)), ('Chen', (593, 283, 779, 97))]
    

    我试过这个代码:

    for i in ap:
        for j in ap:
            if i[1] == j[1]:
                if i[0] == "unknown":
                    del i
                else:
                    del j
    

    Traceback (most recent call last):
      File "<stdin>", line 3, in <module>
    NameError: name 'i' is not defined
    

    怎么了?

    4 回复  |  直到 6 年前
        1
  •  2
  •   PL200    6 年前

    简单明了的答案是:列表理解

    ap = [    ('unknown', (81, 717, 236, 562)), 
              ('unknown', (558, 1033, 825, 765)), 
              ('unknown', (96, 1142, 225, 1013)), 
              ('Jenny', (558, 1033, 825, 765)), 
              ('unknown', (477, 1233, 632, 1078)), 
              ('unknown', (741, 1199, 868, 1070)), 
              ('Garry', (53, 282, 182, 153)), 
              ('Sam', (477, 1233, 632, 1078)), 
              ('Chen', (593, 283, 779, 97)), 
              ('Steve', (741, 1199, 868, 1070)), 
              ('unknown', (53, 282, 182, 153)), 
              ('Harry', (81, 717, 236, 562)), 
              ('unknown', (593, 283, 779, 97))]
    
    known = [my_tuple[1] for my_tuple in ap if my_tuple[0] != "unknown"]
    output = [my_tuple for my_tuple in ap if (my_tuple[1] in known and my_tuple[0] != "unknown") or my_tuple[1] not in known]
    
    print(output)
    

    [('unknown', (96, 1142, 225, 1013)), ('Jenny', (558, 1033, 825, 765)), ('Garry', (53, 282, 182, 153)), ('Sam', (477, 1233, 632, 1078)), ('Chen', (593, 283, 779, 97)), ('Steve', (741, 1199, 868, 1070)), ('Harry', (81, 717, 236, 562))]
    

    这里发生的事情是,我们将所有的第二元组元素收集到一个列表中,其中的名称不是“未知”(使用列表理解)。

    听起来可能有点混乱,希望你能理解我的意思。如果你有任何问题,请告诉我。

        2
  •  2
  •   Community CDub    4 年前

    del 陈述

    删除一个名称将从本地或本地数据库中删除该名称的绑定 全局命名空间,取决于名称是否出现在全局命名空间中 将引发异常。

    用起来更好 dictionary 对于此任务。

    expected = [('Harry',(81, 717, 236, 562)), ('Jenny', (558, 1033, 825, 765)),
    ('unknown', (96, 1142, 225, 1013)), ('Sam', (477, 1233, 632, 1078)),
    ('Steve', (741, 1199, 868, 1070)), ('Garry', (53, 282, 182, 153)), ('Chen', (593, 283, 779, 97))]
    
    
    person_dict = {}
    
    for person_name, person_val in ap:
        
        if person_val not in person_dict:
            # create key using tuple item 2
            person_dict[ person_val] =  person_name
        
        # key already exist so we only want to update its value if it is still unknown
        elif person_dict[ person_val] == 'unknown':
            person_dict[ person_val] =  person_name
            
            
    ap = [(v,k) for k, v in person_dict.items()]
    
    print(ap == expected) # True
    
        3
  •  0
  •   SamGhatak    6 年前

    在两个循环中使用同一个集合,并从循环中的集合中删除,这就产生了问题。我认为最好是创建一个新的项目列表,在这个循环之后删除它们。

    toDelete = []
    for i in ap:
        for j in ap:
            if i[1] == j[1] and not ap.index(i) == ap.index(j):
                if i[0] == "unknown":
                    toDelete.append(i)
                else:
                    toDelete.append(j)
    
    for i in toDelete:
        try:
            ap.remove(i)
        except Exception as e:
            pass
    

    可以通过将第二个循环看作:

    for j in ap[ap.index(i)+1:]:
    
        4
  •  0
  •   toti08    6 年前

    另一种方法是 collections 在原始列表中创建一个重复的列表,然后通过检查哪个元素是重复的来创建一个新的元组列表。然后创建一个新列表,检查哪个元素不重复,或者哪个元素不重复 unknown :

    import collections
    
    # Create a list of elements that are duplicate in the original list
    duplicates = [item for item, count in collections.Counter([x[1] for x in ap]).items() if count > 1]
    
    
    new = []
    for elem in ap:
        if elem[1] in duplicates:
            if elem[0] != 'unknown':
                # Copy the duplicate element only if it's not unknown
                new.append(elem)
        else:
    
            new.append(elem)
    print 'New list: ',new
    

    输出为:

    new list:  [('unknown', (96, 1142, 225, 1013)), ('Jenny', (558, 1033, 825, 765)), ('Garry', (53, 282, 182, 153)), ('Sam', (477, 1233, 632, 1078)), ('Chen', (593, 283, 779, 97)), ('Steve', (741, 1199, 868, 1070)), ('Harry', (81, 717, 236, 562))]