我需要编写一个获取列表的函数,并从该列表中删除两个相同项之间的所有项(并保留其中一个相同的项)。
例如
list1 = ['a', 'b', 1, 'c', 'd', 'e', 'f', 'g', 'h', 1, 'i', 'j']
list2 = ['a', 'b', 1, 'c', '2', 'd', '2', 'e', 'f', 1, 'g', 'h']
list3 = ['a', 1, 'b', 'c', 1, 'd', 2, 'e', 'f', 2, 'g']
print(funct(list1))
print(funct(list2))
print(funct(list3))
将导致:
['a', 'b', 1, 'i', 'j']
['a', 'b', 1, 'g', 'h']
['a', 1, 'd', 2, 'g']
您可以假设列表中的任何第二个重复块实例始终是完全独立的,或者完全在另一个块中。
例如
['a', 1, 'b', 2, 'c', 2, 'd', 1, 'e']
或
['a', 1, 'b', 1, 'c', 2, 'd', 2, 'e']
但从不
['a', 1, 'b', 2, 'c', 1, 'd', 2, 'e']
我已经编写了一个代码来执行此操作,但不喜欢创建单独列表,并将项目附加到该列表,而只是从原始列表中删除项目。
这就是我所拥有的,非常感谢任何帮助:)
def funct(list):
unlooped = []
appending = True
list_index = 1
for item in list:
if appending:
unlooped.append(item)
elif item == looper:
appending = True
if item in list[list_index:] and appending:
appending = False
looper = item
list_index += 1
return unlooped
答案 0 :(得分:1)
怎么样:
def unloop(ls):
return [x for i,x in enumerate(ls) if not set(ls[:i]).intersection(set(ls[i:]))]
说明:如果项x
和i
的交集为空,则在ls
的{{1}}位置取项[0..i-1]
,即之前和之前都没有元素出现在[i..n]
之后。
它适用于您提供的3个示例,可能需要针对边缘情况进行测试
答案 1 :(得分:1)
你写了"我已经编写了一个代码来执行此操作,但不喜欢创建单独的列表,并将项目附加到该列表,而只是从原始列表中删除项目"我认为这意味着从原始列表中删除项目,所以我写了一个解决方案,从列表中删除整个切片。使用列表推导只是创建另一个列表并将项目附加到其中的另一种方式,因此我想避免这种方法。
def unloop(lst):
for i, v in enumerate(lst):
try:
j = lst.index(v, i+1)
lst[i:j] = []
except ValueError:
pass
return lst
我认为有办法让这个算法更有效率。我会考虑一下。就像旁注一样,养成避免与内置对象发生名称冲突的习惯是很好的。例如,如果您有一个名为list
的变量,您会发现很难使用内置的list
名称将其他类型的迭代转换为列表。