关于python可迭代理解的一般问题:
为什么这样的声明
[s for s in x if s>2]
if
紧跟在for
之后,但对于类似
[s if s>2 else None for s in x]
if... else
在for
之前吗?
答案 0 :(得分:9)
条件表达式和理解过滤器唯一的共同点是关键字 if
的共享使用。
a if b else c
是一个条件表达式。目的是保证b
是否为真。它的使用不特定于列表理解;在[s if s > 2 else None for s in x]
中,它只是用作为新列表提供值的表达式,给定s
中的值x
。
if
的另一种用法是列表理解本身语法的一部分。它不是表达式的一部分;它指定一个 filter ,该过滤器用于确定是否应将可迭代对象中的特定值传递给表达式。
如果您将列表理解视为map
和filter
的组合,则该表达式代替map
的函数参数,而if
filter代替对filter
的调用。也就是说,您可以重写任何常规列表理解
[ <expression> for s in xs if <p>]
作为map
和filter
的组合,因此:
list(map(lambda s: <expression>, filter(lambda s: <p>, xs)))
您可以看到PEP-202的有关列表推导的讨论(尽管它比较老,并且没有记录可能考虑过的其他语法),而PEP-308则是关于条件表达式的 讨论了考虑的一些其他语法。
答案 1 :(得分:2)
if-else
不仅限于列表理解,还可以用于赋值语句等。在列表理解中没有特殊含义。
if
表达式之后的for
语法选择了包含在理解中的元素,if-else
无法做到,因此其用法特定于理解。
答案 2 :(得分:0)
在第一种情况下,if
是所创建列表的每个元素是什么的表达式的一部分;在第二步中,它决定是否包含一个元素(因此不需要else
)。
答案 3 :(得分:0)
列表理解的最一般形式是:
[expression1_of_x for x in iterable if expression2_of_x]
,其中expressio2_of_x
是可选的。
因此,以下所有列表理解都可以接受:(expression1_of_x
,expressio2_of_x
)
1. [s for s in x if s>2]
可以。 (s,s> 2)
2. [s if s>2 else None for s in x]
(如果s> 2则为s,否则为None,nil)
3. [s if s>2 else None for s in x if s > 10]
(如果s> 2则为s,否则为s> 10)
有关更多信息,请参见the docs。