(2010 年 11 月 23 日 19:48 回答)
我并不是一个真正的 Python 爱好者——但我曾经发现过这种语法,忘记了从哪里来,所以我想我会记录下来:
如果您使用sys.stdout.write
而不是print
(区别在于,sys.stdout.write
将参数作为函数,在括号中 - 而print
不是),那么对于单行,您可以通过反转命令和 的顺序for
,删除分号,并将命令括在方括号中,即:
python -c "import sys; [sys.stdout.write('rob\n') for r in range(10)]"
不知道如何在 Python 中调用此语法 :)
希望这可以帮助,
干杯!
(2013 年 4 月 9 日星期二 20:57:30 编辑)好吧,我想我终于找到了单行中的这些方括号的含义;它们是“列表理解”(显然);首先在 Python 2.7 中注意这一点:
$ STR=abc
$ echo $STR | python -c "import sys,re; a=(sys.stdout.write(line) for line in sys.stdin); print a"
<generator object <genexpr> at 0xb771461c>
因此圆括号/括号中的命令被视为“生成器对象”;如果我们通过调用“迭代”它next()
- 那么括号内的命令将被执行(注意输出中的“abc”):
$ echo $STR | python -c "import sys,re; a=(sys.stdout.write(line) for line in sys.stdin); a.next() ; print a"
abc
<generator object <genexpr> at 0xb777b734>
如果我们现在使用方括号 - 请注意,我们不需要调用next()
来执行命令,它会在分配后立即执行;a
然而,后来的检查表明None
:
$ echo $STR | python -c "import sys,re; a=[sys.stdout.write(line) for line in sys.stdin]; print a"
abc
[None]
对于方括号的情况,这并没有留下太多信息可供查找 - 但我偶然发现了这个页面,我认为它解释了:
Python Tips and Tricks - 第一版 - Python 教程 | Dream.In .代码:
如果您还记得,单行生成器的标准格式是括号内的一种单行“for”循环。这将产生一个“单次”可迭代对象,这是一个您只能在一个方向上迭代的对象,一旦到达终点就不能重复使用。
“列表推导”看起来与常规的单行生成器几乎相同,除了常规括号 - ( ) - 被方括号 - [ ] 替换。alist 理解的主要优点是产生一个“列表”,而不是一个“一次性”的可迭代对象,这样你就可以来回遍历它、添加元素、排序等。
实际上它是一个列表——它只是它的第一个元素在执行后立即变为 none:
$ echo $STR | python -c "import sys,re; print [sys.stdout.write(line) for line in sys.stdin].__class__"
abc
<type 'list'>
$ echo $STR | python -c "import sys,re; print [sys.stdout.write(line) for line in sys.stdin][0]"
abc
None
列表推导式在5. 数据结构:5.1.4中另有说明。List Comprehensions — Python v2.7.4 文档作为“列表理解提供了一种创建列表的简洁方法”;据推测,这就是列表的有限“可执行性”在单行中发挥作用的地方。
好吧,希望我在这里不会太离谱......
EDIT2:这是一个带有两个非嵌套for循环的单行命令行;都包含在“列表理解”方括号内:
$ echo $STR | python -c "import sys,re; a=[sys.stdout.write(line) for line in sys.stdin]; b=[sys.stdout.write(str(x)) for x in range(2)] ; print a ; print b"
abc
01[None]
[None, None]
请注意,第二个“列表”b
现在有两个元素,因为它的 for 循环显式运行了两次;但是,sys.stdout.write()
这两种情况的结果都是(显然)None
。