压缩list.py的程序

时间:2017-01-28 12:03:04

标签: python

我正在尝试编写一个接受字符列表的函数,并返回由列表中重复的字符组成的元组列表以及它们重复的次数。例如:如果我有一个列表,例如:["a", "a", "b", "b", "b", "c", "a", "a"] 它应该返回:

[('a', 2), ('b', 3), ('c', 1), ('a', 2)]

我为此编写了一个代码,但我得到的输出是:

[('a', 2), ('b', 3), ('c', 1)]

这是我的代码:

def comress(lst):
    i = 0
    counter = 0
    new_list = []
    while i < len(lst) -1:
        if lst[i] == lst[i+1]:
            counter += 1
            i += 1
        else:
            counter += 1
            tup = (lst[i], counter)
            new_list.append(tup)
            counter = 0
            i += 1

    return new_list
a = ["a", "a", "b", "b", "b", "c", "a", "a"]
print(comress(a))

我不知道问题是什么。我想听听你的意见。提前谢谢。

6 个答案:

答案 0 :(得分:2)

使用collections.Counter()itertools.groupby()方法的一个班轮。

from itertools import groupby
from collections import Counter

l1 = ["a", "a", "b", "b", "b", "c", "a", "a"]
print [Counter(g).items()[0] for _, g in groupby(l1)]

输出:

[('a', 2), ('b', 3), ('c', 1), ('a', 2)]

答案 1 :(得分:2)

如果值与前一个值相同,则不需要保留额外的计数器,只需增加元组中的计数器:

def compress(lst):
    res = [(lst[0], 1)]  #  take first value
    for val in lst[1:]:  #  go through the rest of the values
        if val == res[-1][0]:  #  if the value is the same as the last one in res
            res[-1] = (val, res[-1][-1] + 1)   #  increment the count
        else:   # otherwise
            res.append((val, 1))  #  add a new value-count pair
    return res

print(compress(lst))

输出:

[('a', 2), ('b', 3), ('c', 1), ('a', 2)]

答案 2 :(得分:1)

当前字符与上一个字符不同时,您的代码只会附加到new_list。当列表遍历结束时,它会忽略最后一行字符。

答案 3 :(得分:1)

当涉及到最后一项时,您的代码不会插入到列表中,如果它们相等,则不会插入它们。

你需要检查最后的项目,如果它们是相同的,那么也插入它们,如下所示:

lst= ["a", "a", "b", "b", "b", "c", "a", "a"]
def comress(lst):
    i = 0
    counter = 0
    new_list = []
    while i < len(lst) - 1:
        if lst[i] == lst[i+1]:
            counter += 1
            i += 1
        else:
            counter += 1
            tup = (lst[i], counter)
            new_list.append(tup)
            counter = 0
            i += 1
        if i + 1 == len(lst) and lst[i] == lst[i-1]:
            counter +=1
            tup = (lst[i], counter)
            new_list.append(tup)

    return new_list
a = ["a", "a", "b", "b", "b", "c", "a", "a"]
print(comress(a))

>>> [('a', 2), ('b', 3), ('c', 1), ('a', 2)]

答案 4 :(得分:1)

您可以尝试使用itertools.groupby

from itertools import groupby
L = ["a", "a", "b", "b", "b", "c", "a", "a"]
newL = []
for k, g in groupby(L):
    tempL = list(g)
    newL.append((k, len(tempL)))

答案 5 :(得分:0)

这可能是使用您的计数器逻辑的最pythonic解决方案:

def comress(lst):
    counter = 1
    new_list = []
    for val1, val2 in zip(lst[:-1], lst[1:]):
        if val1 == val2:
            counter += 1
        else:
            new_list.append((val1, counter))
            counter = 1
    new_list.append((val2, counter))
    return new_list

​    
a = ["a", "a", "b", "b", "b", "c", "a", "a"]
print(comress(a))

输出:

[('a', 2), ('b', 3), ('c', 1), ('a', 2)]