pep*_*nas 5 python membership containers generator data-structures
这是我的Python代码:
# 1)
if (x not in z for z in y):
# 2)
if (x not in y):
Run Code Online (Sandbox Code Playgroud)
其中y可以是如下列表:
y = ['1','2','3']
Run Code Online (Sandbox Code Playgroud)
有人能解释一下这两句话的区别吗?谢谢!
首先,(x not in z for z in y)是一个生成器语句,如果if在它前面,它将始终返回True.
if (x not in z for z in y): # Always returns True
Run Code Online (Sandbox Code Playgroud)
这可以用于查看是否包含任何或所有嵌套的iterables x.
例如
if any(x in z for z in y): # Returns True if any of the z's contain x
if all(x in z for z in y): # Returns True only if all of the z's contain x
Run Code Online (Sandbox Code Playgroud)
所以如果y是这样的话:
y = ['hello','how','are','you']
Run Code Online (Sandbox Code Playgroud)
然后,如果x是,例如,'e'那么any上面的理解将返回True,但all理解将返回False.
所以这就是生成器理解中发生的事情:如果y是一个列表,那么你测试:
(x not in z for z in y)
Run Code Online (Sandbox Code Playgroud)
y中的z必须是可迭代的,以便测试包含,哪些字符串是,但是你只是看到在这种情况下某些东西是长度为1的字符串.一个更好的例子是使用整数:
y = [1, 2, 3]
Run Code Online (Sandbox Code Playgroud)
和
if (x not in z for z in y):
Run Code Online (Sandbox Code Playgroud)
会失败,因为整数不可迭代,但是
if (x not in y):
Run Code Online (Sandbox Code Playgroud)
会成功,因为你可以测试实际列表中的成员资格.
当你有
y = ['1','2','3']
Run Code Online (Sandbox Code Playgroud)
类似的嵌套级别是:
y = [(1,), (2,), (3,)]
Run Code Online (Sandbox Code Playgroud)
与
(x not in z for z in y)
Run Code Online (Sandbox Code Playgroud)
你正在测试x是否在其中一个元组中.
那有意义吗?
让\xe2\x80\x99s 首先从简单的开始:
\n\nif (x not in y):\nRun Code Online (Sandbox Code Playgroud)\n\n括号 don\xe2\x80\x99t 在那里具有任何含义,因此这相当于:
\n\nif x not in y:\nRun Code Online (Sandbox Code Playgroud)\n\n操作in员检查某些内容是否包含在其他内容中。就您而言,您有一个列表y,因此您要检查该列表( x)中是否不包含某些内容( ) 。所以会是因为是 的元素,并且会是因为不是 的元素。not iny\'1\' not in yFalse\'1\'y\'4\' not in yTrue\'4\'y
另一种则完全不同:
\n\nif (x not in z for z in y)\nRun Code Online (Sandbox Code Playgroud)\n\n这里我们有一个生成器表达式。生成器表达式的格式(x for z in y)与此代码等效:
for z in y:\n yield x\nRun Code Online (Sandbox Code Playgroud)\n\n您以前可能听说过列表推导式;它们很相似,但使用方括号而不是圆括号:[x for z in y]。当他们返回一个列表时,他们更容易理解。它们等价于:
lst = []\nfor z in y:\n lst.append(x)\nreturn lst\nRun Code Online (Sandbox Code Playgroud)\n\n本质上,您正在循环 的元素y,在迭代中调用每个元素\nz并返回x该元素。在您的情况下,x是一个表达式本身:x not in z与上面基本相同:您正在检查是否x不包含在 中 z。
现在,生成器表达式有点复杂,因为它们是在请求元素时计算的,所以让\xe2\x80\x99s 现在假设我们有一个列表理解
\n\nif [x not in z for z in y]:\nRun Code Online (Sandbox Code Playgroud)\n\n所以它的作用是计算中的x not in z每个元素。因此,对于您的,结果列表将是这样的:zyy
[x not in \'1\', x not in \'2\', x not in \'3\']\nRun Code Online (Sandbox Code Playgroud)\n\n对于 real x,这将产生一个包含三个布尔值的列表。现在非空列表总是 trueish,因此无论此检查的结果如何,-checkif都会成功。
不过,生成器表达式将返回一个生成器,它是一个比列表更复杂的对象。不过,这也是真实的,因此无论各个值如何,您的检查也会成功。
\n\n现在想象一下,我们想要确保,对于列表中的这三个元素,我们希望所有检查的结果都是True。为此,我们可以使用all()本质上检查列表\xe2\x80\x94 或生成器\xe2\x80\x94 中的值是否仅包含真值的函数。
if all(x not in z for z in y):\nRun Code Online (Sandbox Code Playgroud)\n\nx因此,如果不包含在列表的任何元素中,则这将成功y。另一方面,如果我们想检查列表或生成器中是否至少有一个真实值,那么我们可以使用该any()函数。