如何在Python中从列表中删除所有整数值

19

我只是Python的初学者,想知道是否有可能从列表中删除所有整数值?例如,文档如下

['1','introduction','to','molecular','8','the','learning','module','5']

移除后,我想让文档看起来像这样:

['introduction','to','molecular','the','learning','module']
8个回答

42

要删除所有整数,请执行以下操作:

no_integers = [x for x in mylist if not isinstance(x, int)]

然而,您的示例列表实际上并不包含整数。 它仅包含字符串,其中一些仅由数字组成。 要过滤掉这些字符串,请执行以下操作:

no_integers = [x for x in mylist if not (x.isdigit() 
                                         or x[0] == '-' and x[1:].isdigit())]

或者:

is_integer = lambda s: s.isdigit() or (s[0] == '-' and s[1:].isdigit())
no_integers = filter(is_integer, mylist)

1
这些概括使得问题变得不够清晰。建议尝试S. Lott更符合Python风格的答案。 - Seth Johnson
@Daniel Stutzbach:你的过滤函数很棒,但是你应该使用filter()。保持Pythonic风格,你懂的.. - ktdrv
@Brian:我不确定原帖作者是否需要(或想要)过滤十六进制。 - Daniel Stutzbach
@Daniel:没错,但如果你要抱怨不能处理负数,那么你也可以抱怨这个。它也不能处理“+5”。 - Brian
ALTERNATIVE 会返回一个过滤器对象。 使用 list(no_integers) 可以得到一个列表对象。它只会返回数字。 如果要得到不包含数字的列表,请使用: is_not_integer = lambda s: not s.isdigit() and not (s[0] == '-' and s[1:].isdigit()) - MichiBack
显示剩余5条评论

14

您的列表中没有整数项。它们是仅包含数字的字符串。因此,您可以使用 isdigit 字符串方法来过滤这些项。

items = ['1','introduction','to','molecular','8','the','learning','module','5']

new_items = [item for item in items if not item.isdigit()]

print new_items

文档链接:http://docs.python.org/library/stdtypes.html#str.isdigit


13
你也可以这样做:
def int_filter( someList ):
    for v in someList:
        try:
            int(v)
            continue # Skip these
        except ValueError:
            yield v # Keep these

list( int_filter( items ))

为什么?因为使用int比试图编写规则或正则表达式来识别编码整数的字符串值更好。


为什么 intstr.isdigit 更好呢? - Daniel Stutzbach
5
正如其他人指出的那样,'-2'.isdigit() 将返回 False - Seth Johnson
+1. 请参考 https://dev59.com/B3RC5IYBdhLWcg3wRO3k 进行讨论(使用 float,但仍然非常相关)。 - Brian

5

我个人喜欢使用过滤器。如果恰当地使用,它可以帮助保持代码的可读性和概念上的简单性:

x = ['1','introduction','to','molecular','8','the','learning','module','5'] 
x = filter(lambda i: not str.isdigit(i), x)

或者

from itertools import ifilterfalse
x = ifilterfalse(str.isdigit, x)

请注意第二个返回一个迭代器。


2
从列表中删除所有整数。
ls = ['1','introduction','to','molecular','8','the','learning','module','5']
ls_alpha = [i for i in ls if not i.isdigit()]
print(ls_alpha)

1
请不要使用这种方式从列表中删除项目:(在THC4k的评论后编辑)
>>> li = ['1','introduction','to','molecular','8','the','learning','module','5']
>>> for item in li:
        if item.isdigit():
            li.remove(item)

>>> print li
['introduction', 'to', 'molecular', 'the', 'learning', 'module']

这样做是行不通的,因为在迭代列表时更改它会使for循环混乱。 此外,如果item是包含负整数的字符串,则item.isdigit()将无法正常工作,如razpeitia所指出的那样。


Python真的需要一种机制来防止人们这样做。看起来它会起作用,但实际上并不会——尝试使用li = ['iterating + removing -> skipping', '4', '5', 'see?'](删除4将跳过5,因此它仍然在列表中)。 - Jochen Ritzel

1

你也可以使用lambda表达式(和递归),来实现这个功能(需要Python 3):

 isNumber = lambda s: False if ( not( s[0].isdigit() ) and s[0]!='+' and s[0]!='-' ) else isNumberBody( s[ 1:] )

 isNumberBody = lambda s: True if len( s ) == 0 else ( False if ( not( s[0].isdigit() ) and s[0]!='.' ) else isNumberBody( s[ 1:] ) )

 removeNumbers = lambda s: [] if len( s ) == 0 else ( ( [s[0]] + removeNumbers(s[1:]) ) if ( not( isInteger( s[0] ) ) ) else [] + removeNumbers( s[ 1:] ) )

 l = removeNumbers(["hello", "-1", "2", "world", "+23.45"])
 print( l )

结果(从“l”显示)将是:['你好','世界']


嗯,是的,但更改那段代码以实现该行为将是微不足道的。 - Baltasarq
完成,现在它可以处理负数。 - Baltasarq

0
你可以使用内置的filter函数来获取列表的过滤副本。
>>> the_list = ['1','introduction','to','molecular',-8,'the','learning','module',5L]
>>> the_list = filter(lambda s: not str(s).lstrip('-').isdigit(), the_list)
>>> the_list
['introduction', 'to', 'molecular', 'the', 'learning', 'module']

上述代码可以通过使用显式类型转换来处理各种对象。由于几乎每个Python对象都可以合法地转换为字符串,因此在这里,filter为the_list的每个成员获取了一个转换为字符串的副本,并检查该字符串(减去任何前导“-”字符)是否是数字。如果是,则将该成员从返回的副本中排除。

内置函数非常有用。它们都针对它们设计要处理的任务进行了高度优化,并且它们会使您免于重新发明解决方案。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接