Python,比较子列表和列表

时间:2015-06-05 19:12:54

标签: python comparison append sublist

我有一个包含大量子列表的列表。即。

mylst = [[1, 343, 407, 433, 27], 
         [1, 344, 413, 744, 302], 
         [1, 344, 500, 600, 100], 
         [1, 344, 752, 1114, 363], 
         [1, 345, 755, 922, 168], 
         [2, 345, 188, 1093, 906], 
         [2, 346, 4, 950, 947], 
         [2, 346, 953, 995, 43], 
         [3, 346, 967, 1084, 118], 
         [3, 347, 4, 951, 948], 
         [3, 347, 1053, 1086, 34], 
         [3, 349, 1049, 1125, 77], 
         [3, 349, 1004, 1124, 120], 
         [3, 350, 185, 986, 802], 
         [3, 352, 1018, 1055, 38]]

我想首先开始对此列表进行分类,然后使用三个步骤制作另一个列表。首先,我想比较每个子列表中第一项相同的子列表,即mylist [a] [0] == 1。其次,比较子列表中的第二项,如果子列表中的第二项与下面的2项下的第二项之间的差异,则计算第三项或第四项之间的差异。如果第三项和第四项的差异小于10,那么我想追加子列表的索引。

我想要的结果应该是......像这样:[0, 1, 3, 4, 6, 7, 10, 11, 12]

以下是我天真的尝试。

以下是我天真的尝试。

def seg(mylist) :
    Segments = []
    for a in range(len(mylist)-1) :
        for index, value in enumerate (mylist) :
            if mylist[a][0] == 1 :
                if abs(mylist[a][1] - mylist[a+1][1]) <= 2 :
                    if (abs(mylist[a][2] - mylist[a+1][2]) <= 10 or 
                        abs(mylist[a][3] - mylist[a+1][3]) <= 10) :
                        Segments.append(index)
return Segments

def seg(mylist) :
    Segments= []
    for index, value in enumerate(mylist) :
        for a in range(len(mylist)-1) :
            if mylist[a][0] == 1 :
                try :
                    if abs(mylist[a][1]-mylist[a+1][1]) <= 2 :
                        if (abs(mylist[a][2]-mylist[a+1][2]) <= 10 or
                            abs(mylist[a][3] - mylist[a+1][3]) <= 10) :
                            Segments.append(index)
                except IndexError :
                    if abs(mylist[a][1]-mylist[a+1][1]) <= 2 :
                        if (abs(mylist[a][2]-mylist[a+1][2]) <= 10 or
                            abs(mylist[a][3] - mylist[a+1][3]) <= 10):
                            Segments.append(index)
return Segments

这些代码看起来并不好看,结果并没有像我想的那样显示出来。在最下面的一个,我写了尝试,除了处理索引错误(列表超出范围),最初我使用&#39;而&#39;迭代而不是&#39;迭代。

我该怎样做才能得到我想要的结果?如何更正这些代码看起来更像&#39; pythonic&#39;办法? 任何想法都对我很好,并且提前多多感谢。

2 个答案:

答案 0 :(得分:1)

您必须捕获重复索引,但这应该更有效:

gr = []
it = iter(mylst)
prev = next(it)

for ind, ele in enumerate(it):
    if ele[0] == prev[0] and abs(ele[1] - prev[1]) <= 2:
        if any(abs(ele[i] - prev[i]) < 10 for i in (2, 3)):
            gr.extend((ind, ind+1))
    prev = ele

基于您的逻辑6和7不应出现,因为它们不符合标准:

     [2, 346, 953, 995, 43], 
     [3, 346, 967, 1084, 118], 

根据您的说明,如果要显示10,则<= 2不是< 2

您可以使用OrderedDict删除欺骗并保留顺序:

from collections import OrderedDict

print(OrderedDict.fromkeys(gr).keys())
[0, 1, 3, 4, 10, 11, 12]

答案 1 :(得分:0)

这似乎对我有用。我不确定它是否会以任何方式更多Pythonic而且你将在列表中循环多次,所以你可以做一些事情来更好地优化它。

def seg(mylist):
    # converted list to set in case there are any duplicates
    segments = set()

    for entry_index in range(len(mylist)):
        for c in range(len(mylist)):
            first = mylist[entry_index]
            comparison = mylist[c]

            # ignore comparing the same items
            if entry_index == c:
               continue

            # ignore cases where the first item does not match
            if first[0] != comparison[0]:
                continue

            # ignore cases where the second item differs by more than 2
            if abs(first[1] - comparison[1]) > 2:
                continue

            # add cases where the third and fourth items differ by less than 10
            if abs(first[2] - comparison[2]) < 10 or abs(first[3] - comparison[3]) < 10:
                segments.add(entry_index)

            elif abs(first[2] - comparison[3]) < 10 or abs(first[3] - comparison[2]) < 10:
                segments.add(entry_index)

    return segments