如何检查列表中的所有项目是否均为None?


77
In [27]: map( lambda f,p: f.match(p), list(patterns.itervalues()), vatids )
Out[27]: [None, <_sre.SRE_Match object at 0xb73bfdb0>, None]

该列表可以是全部None,也可以是re.Match实例之一。我可以在返回的清单上进行哪一张班轮支票,以告诉我内容全部None


Answers:


176
all(v is None for v in l)

将返回True如果所有的元素lNone

请注意,l.count(None) == len(l)这要快得多,但是要求它l是实际的list而不仅仅是可迭代的。


对于懒惰的人:是指向文档的链接。
Matt3o12

就第一个表达式使用生成器而言,它会在首次None出现时停止吗?对我来说毫无意义。
soupault 2015年

3
@ s0upa1tall在找到第一个伪造对象时停止。第二种方法至少在CPython下更快,因为该类型.count的对象的方法list是内置的并用C编写,并且与生成器不同,它没有在列表循环中涉及解释器。
Dan D.

all(v is None for v in l)如果您0在适当位置安装了None
virtualxtc

49
not any(my_list)

返回True如果所有项目my_list都falsy。

编辑:由于匹配对象始终是虚伪的并且None是虚假的,所以这将产生与all(x is None for x in my_list)手头情况相同的结果。如gnibbler的答案所示any()到目前为止,使用是更快的选择。


8
对于数字值这一个失败小于1被认为falsy
狗吃猫世界

5
@狗:您的评论与这个问题完全无关。匹配对象评估为TrueNone评估为False。此外,只有0被认为是虚假的,而不是“数值小于1”。
Sven Marnach 2011年

2
@Sven,我的评论与这个问题无关吗?他询问了一个可以检测列表是否仅包含None值的函数。您的示例将以与包含[None,None]的列表相同的方式处理[0,None]。我看到关于负数的错误,我不确定我从哪里得到的!
狗吃猫世界

2
@Dog:该问题清楚地说明了该列表由返回值组成,该返回值re.match()None或匹配对象,因此该解决方案不会因失败而无所谓0。我添加了一些解释以使其更清楚。
Sven Marnach 2011年

2
@sleepycal:我通常会尝试给出解决人们问题的答案,而不是确切回答他们认为他们的问题是什么(“ XY问题”)。这个问题使实际问题很清楚(确定列表中的所有模式是否都不匹配),我的答案是对该问题的简洁快速解决方案。
Sven Marnach 2014年

15

由于Match对象永远不会评估为false,因此可以使用并且可以更快地进行操作 not any(L)

$ python -m timeit -s"L=[None,None,None]" "all( v is None for v in L )"
100000 loops, best of 3: 1.52 usec per loop
$ python -m timeit -s"L=[None,None,None]" "not any(L)"
1000000 loops, best of 3: 0.281 usec per loop

$ python -m timeit -s"L=[None,1,None]" "all( v is None for v in L )"
100000 loops, best of 3: 1.81 usec per loop
$ python -m timeit -s"L=[None,1,None]" "not any(L)"
1000000 loops, best of 3: 0.272 usec per loop

6

还是有点怪,但是:

a = [None, None, None]
set(a) == set([None])

要么:

if [x for x in a if x]: # non empty list
    #do something   

编辑:

def is_empty(lVals):
    if not lVals:
        return True
    for x in lVals:
        if x:
            return False
    return True

2
这两个都需要遍历整个列表,即使第一个元素不是None。
约翰·拉鲁伊

@gnibbler-是的,您是对的,添加了一个不会迭代所有项目的“丑陋”解决方案
Artsiom Rudzenka 2011年

的更简洁的定义is_empty(my_list)return not any(my_list)。至少,您应该省略前两行。
Sven Marnach 2011年

@Sven-是的-没错,只是尝试不重复其他解决方案,而是提供相同的功能。我知道已经讨论过了,“所有”方法都是专家方法)),但我不是专家–我只是在学习新东西
Artioom Rudzenka 2011年

0
is_all_none = lambda L: not len(filter(lambda e: not e is None, L))

is_all_none([None,None,'x'])
False
is_all_none([None,None,None])
True

除了与标准答案相比非常冗长外,它使我感到困惑,为什么您会lambda在这里使用它而不是简单的def
RoundTower 2011年

@RoundTower,因为他要单线。我猜测他会把它用作内联函数,因为他已经在示例中使用了lambda函数。
狗吃猫世界

@RoundTower“挡板”?当您在函数周围包含必需的空白行时,def会再增加几行。我不明白为什么python程序员不关心代码长度膨胀-屏幕空间要大得多。我们不是在谈论冷凝50行成一个一拉”的Perl代码高尔夫也一行或两行没有扩大到5或10
StephenBoesch

0

我设法提出一种map尚未使用的方法

tl; dr

def all_none(l):
    return not any(map(None.__ne__, l))

all_none([None, None, None]) # -> True
all_none([None, None, 8])    # -> False

说明

None.__ne__乍看之下,使用有点奇怪。NotImplementedType当给定的值不是None时,此方法将返回一个对象。

您希望这NotImplemented将是的替代False,但这也是事实!这意味着None.__eq__在集合中使用将为所有内容产生真正的价值。

list(map(None.__eq__, [None, None, 8]))
# -> [True, True, NotImplemented]

all(list(map(None.__eq__, [None, None, 8])))
# -> True

Python文档

默认情况下,除非对象的类定义了返回False的bool()方法或返回零的len()方法,否则将其视为true。

相反,None.__ne__返回False任何None元素,返回一个 NotImplementedType对象作为其他对象:

list(map(None.__ne__, [None, None, 8]))
# -> [False, False, NotImplemented]

使用此方法,您可以检查any元素是否不None返回True。我想将其视为2种单独的方法,以帮助进行精神否定体操。

def contains_truthy(l):
    return any(map(None.__ne__, l))

def all_none(l):
    return not contains_truthy(l)

我没有对此进行任何基准测试,但是正如该线程中的其他人所提到的,not any将产生快速的结果。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.