简体   繁体   English

Python不会从列表中删除项目

[英]Python wont remove items from list

filtered_list = ['PerezHilton', 'tomCruise', 'q', 'p']
#BIO[user]['follows'] is just a list of strings say ['a', 'b', 'katieh']
#specs is also a string say eg. 'katieh'
for user in filtered_list:
    if specs not in BIO[user]['follows']:
        filtered_list.remove(user)

The above code for some reson gives this error "ValueError: list.remove(x): x not in list" but clearly 'p' is in the list so why is it not detecting 'p' but it is finding 'q'?? 上面针对某些共振的代码给出了此错误“ ValueError:list.remove(x):x不在列表中”,但显然“ p”在列表中,所以为什么它不检测“ p”却在查找“ q”? ?

Im soo stumped but any help is appreciated, thanks 我很沮丧,但是感谢您的任何帮助,谢谢

** SORRY i FIXED IT NOW * **抱歉,我现在已修复*

The list comprehension that does this correctly in one line is at the bottom of the post. 列表理解可以在一行中正确完成,位于文章的底部。 Here's some insight into the problem first. 首先是对问题的一些了解。

Don't do things like: 不要做类似的事情:

for item in list_:
    list_.remove(item)

because bad and confusing things happen. 因为坏事和令人困惑的事情发生了。

>>> list_ = range(10)
>>> for item in list_:
...     list_.remove(item)
... 
>>> list_
[1, 3, 5, 7, 9]

Every time you remove an item, you change the indexes for the rest of the items which messes up the loop. 每次删除项目时,您都会更改其余项目的索引,这会弄乱循环。 One good way to remove items from a list while you're traversing it is to do it by index and work backwards so that removals don't affect the rest of the iterations. 在遍历列表时从列表中删除项目的一种好方法是按索引进行操作并向后工作,以使删除不会影响其余的迭代。 This is better because if you remove the 9'th element, then the 8'th element is still the 8'th element but the 10'th element becomes the 9'th element. 这样做会更好,因为如果删除第9个元素,那么第8个元素仍然是第8个元素,而第10个元素将成为第9个元素。 If you've already dealt with that element, then you don't care what its index is. 如果您已经处理过该元素,那么您不必关心它的索引是什么。

>>> list_ = range(10)
>>> for i in xrange(len(list_) - 1, -1, -1):
...     del list_[i]
... 
>>> list_
[]

Or with a while loop: 或使用while循环:

i = len(list_)
while i:
    i -= 1
    del list_[i]

So in your case, the code would look something like 因此,在您的情况下,代码看起来像

users[:] = [user for user in users if specs in BIO[user]['follows']]

because this is a filtering job and those are best done with list comprehensions. 因为这是一项筛选工作,而最好使用列表推导来完成。 The point of the [:] is that it assigns to a slice of the list instead of clobbering the reference to the list. [:]的要点是,它分配给列表的一部分,而不是破坏对列表的引用。 This means that every other reference to the list will be updated. 这意味着对列表的所有其他引用都将被更新。 It's essentially in-place, except that a copy is made before overwriting the original list. 它本质上是原地的,除了副本覆盖原来的名单之前进行。 For the sake of completeness, here's how to do it with a while loop. 为了完整起见,下面是使用while循环的方法。

i = len(users)
while i:
    i -= 1
    if specs not in BIO[users[i]]['follows']:
        del users[i]

You could do this if you wanted it done in place. 如果您希望它就位,则可以执行此操作。 No copy of the list is made here. 此处没有列表的副本。

Why are you iterating? 你为什么要迭代?

>>> un = ['PerezHilton', 'tomCruise', 'q', 'p']
>>> un.remove('p')
>>> un
['PerezHilton', 'tomCruise', 'q']

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM