我有一个清单:
mylist = ['apple', 'orange', 'dragon', 'panda']
我希望能够遍历列表,对每个元素执行某些操作然后删除元素。我试过这个:
for l in mylist:
print l
list.remove(l)
但我的输出是:
apple
dragon
修改
我实际上希望能够在循环中进行一些比较。所以基本上我希望能够逐个取出每个元素,删除列表中的元素,并将其与列表中的所有其他元素进行比较。比较有点复杂,所以我不想使用列表理解。我希望每次减少一个列表,直到列表为空并且所有元素都已相互比较。
获取每个元素,使用它并删除它而不跳过列表中元素的最佳方法是什么?
任何帮助,非常感谢。
REDIT
只是要说清楚 - 真正的要点是遍历每个元素,这是一个字符串片段,并将其与任何一端具有重叠序列的其他片段匹配,从而构建完整的序列。在循环之前,应该从列表中删除正在处理的元素,这样它就不会与它自身进行比较,并且每个处理循环的列表应该缩小1个元素。
如果是更好的列表示例:
mylist = ['apples and or', 'oranges have', 'in common', 'e nothing in c']
给予:
'apples and oranges have nothing in common'
抱歉从一开始就不清楚,但这是我坚持的这个更大问题的一个特定部分。
答案 0 :(得分:3)
您可以反转列表顺序(如果您想按原始顺序处理项目),然后使用pop()获取项目并依次删除它们:
my_list = ['apple', 'orange', 'dragon', 'panda']
my_list.reverse()
while my_list:
print(my_list.pop())
答案 1 :(得分:3)
根据您的要求,您希望“能够将每个元素一个接一个地用于列表,并将其与列表中的所有其他元素进行比较”,我相信您是最好的适合使用itertools。在这里,如果没有从列表中删除元素的效率低下,您就可以获得防范,以便将每个组合彼此进行一次比较。由于您的规范似乎没有为删除提供任何用途(除了实现组合的目标),我觉得这很有效。
也就是说,在我看来,列表推导将是解决这个问题的最常见方式,因为它不会影响进行复杂比较的任何能力。
import itertools
l = ['apple', 'orange', 'dragon', 'panda']
def yourfunc(a,b):
pass
for a, b in itertools.combinations_with_replacement(l, 2):
yourfunc(a,b)
列表理解方法将改为使用此代码:
[yourfunc(a, b) for a,b in itertools.combinations(l, 2)]
编辑:根据您的其他信息,我相信您应该重新考虑itertools。
import itertools
l = ['apples and or', 'oranges have', 'in common', 'e nothing in c', 'on, dont you know?']
def find_overlap(a,b):
for i in xrange(len(a)):
if a[-i:] == b[0:i]:
return a + b[i:]
return ''
def reduce_combinations(fragments):
matches = []
for c in itertools.combinations(fragments, 2):
f = reduce(find_overlap, c[1:], c[0])
if f: matches.append(f)
return matches
copy = l
while len(copy) > 1:
copy = reduce_combinations(copy)
print copy
返回
['apples and oranges have nothing in common, dont you know?']
**编辑:(再次)。 **这种排列是一种实用的解决方案,并且具有额外的好处 - 虽然比上述解决方案有更多的计算,但将提供所有可能的技术匹配。上述解决方案的问题在于它只需要一个答案,这可以通过while循环来证明。因此,它更有效率,但如果存在多个答案,也可能无法返回任何内容。
import itertools
l = ['apples and or', 'oranges have', 'in common', 'e nothing in c', 'on, dont you know?']
def find_overlap(a,b):
for i in xrange(len(a)):
if a[-i:] == b[0:i]:
return a + b[i:]
return ''
matches = []
for c in itertools.combinations(l, 2):
f = reduce(find_overlap, c[1:], c[0])
if f: matches.append(f)
for c in itertools.combinations(matches, len(matches)):
f = reduce(find_overlap, c[1:], c[0])
if f: print f
答案 2 :(得分:1)
有什么理由你不能简单地遍历所有元素,对它们做些什么,然后将列表重置为空列表?类似的东西:
for l in my_list:
print l
my_list = []
# or, if you want to mutate the actual list object, and not just re-assign
# a blank list to my_list
my_list[:] = []
修改强>
根据您的更新,您需要做的是使用已提到的弹出方法:
while len(my_list):
item = my_list.pop()
do_some_complicated_comparisons(item)
如果您关心订单,那么只需从前面弹出:
my_list.pop(0)
或在循环之前反转列表:
my_list.reverse()
答案 3 :(得分:0)
迭代列表时无法删除元素。处理元素,然后处理列表。所有编程语言都是如此,而不仅仅是Python,因为它会导致这些跳过问题。
作为替代方案,您可以在完成元素后执行list = []
。
答案 4 :(得分:0)
如果转发顺序无关紧要,我可能会这样做:
l = ['apple', 'orange', 'dragon', 'panda']
while l:
print l.pop()
鉴于您的编辑,一个很好的选择是使用deque
而不是列表。
>>> import collections
>>> l = ['apple', 'orange', 'dragon', 'panda']
>>> d = collections.deque(l)
>>> while d:
i = d.popleft()
for j in d:
if i > j: print (i, j)
...
('orange', 'dragon')
使用deque
很好,因为从任一端弹出是O(1)。最好不要使用deque
进行随机访问,因为这比列表慢。
另一方面,由于您每次都在遍历整个列表,因此无论如何,代码的渐近性能将为O(n ** 2)。因此,使用列表并从pop(0)
开头弹出是正确的,从渐近的角度来看是合理的(尽管它比使用deque
一些常数倍更慢)。
但实际上,由于你的目标似乎是生成组合,你应该考虑hexparrot的答案,这是非常优雅的 - 虽然在性能方面,它不应该与上述基于deque
的解决方案完全不同,因为从deque
删除项目很便宜。
答案 5 :(得分:0)
制作副本:
for l in original[:]:
print l
original.remove(l)
答案 6 :(得分:0)
您可以使用堆栈操作来实现:
while len(mylist):
myitem = mylist.pop(0)
# Do something with myitem
# ...
答案 7 :(得分:0)
#! C:\python27
import string
list = ['apple', 'orange', 'dragon', 'panda']
print list
myLength = len(list) -1
print myLength
del list[myLength]
print list
[编辑]
继承代码循环并查找用户输入并删除它的单词。
#! C:\python27
import string
whattofind = raw_input("What shall we look for and delete?")
myList = ['apple', 'orange', 'dragon', 'panda']
print myList
for item in myList:
if whattofind in myList:
myList.remove(whattofind)
print myList
答案 8 :(得分:0)
嗯..看到你无法以这种方式删除所有项目,即使你遍历所有这些项目..试试这个:
#! C:\python27
list1 = ["apple","pear","falcon","bear"] #define list 1
list2 = [] #define list 2
item2 ="" #define temp item
for item in list1[:]:
item2 = item+"2" #take current item from list 2 and do something. (Add 2 in my case)
list2.append(item2) #add modified item to list2
list1.remove(item) #remove the un-needed item from list1
print list1 #becomes empty
print list2 #full and with modified items.
我假设如果你正在进行比较,你可以在''for'之后转储''if''子句以运行比较或其他东西。但这似乎是做到这一点的方式。