是什么使Python3的打印函数线程安全? [英] What makes Python3's print function thread safe?

查看:124
本文介绍了是什么使Python3的打印函数线程安全?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在各种邮件列表和论坛上看到人们不断提到Python 3中的打印功能是线程安全的。从我自己的测试中,我看不出有什么疑问。

 导入线程
导入时间
导入随机

def worker(字母):
print(字母* 50)


线程= [threading.Thread(target = worker,args = (let,))对于 ABCDEFGHIJ中的let:
对于线程中的t:
t.start()
对于线程中的t:
t.join()

当我使用Python 3运行它时,即使某些行可能乱序,它们仍然总是走自己的路。但是,对于Python 2,输出是相当零星的。有些线连接在一起或缩进。当我从__future__导入print_function





我只是想了解为什么会这样?

解决方案

对于Python 3.7: print()函数是内置,默认情况下它将输出发送到 sys.stdout 其中的文档以及其他内容:


交互时,stdout和stderr流是行缓冲的。
否则,它们将像常规文本文件一样被块缓冲。您可以使用-u命令行选项
覆盖此值。


因此,它实际上是交互式模式和<$ c $的组合c> sys.stderr 负责 print 函数的行为,如示例所示。


如果将示例程序中的 worker 函数更改为

  def worker(letter):
print(字母* 25,letter * 25,sep ='\n')

然后我们得到类似于以下内容的输出,该输出清楚地表明 print 本身不是线程安全的,您可以期望的是单独的行没有得到交错彼此。

  DDDDDDDDDDDDDDDDDDDDDDDDDJJJJJJJJJJJJJJJJJJJJJJJJJ 

JJJJJJJJJJJJJJJJJJJJJJJJJ
DDDDDDDDDDDDDDDDDDDDDDDDDGGGGGGGGGGGGGGGGGGGGGGGGG
GGGGGGGGGGGGGGGGGGGGGGGGGAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAHHHHHHHHHHHHHHHHHHHHHHHH
HHHHHHHHHHHHHHHHHHHHHHHHH


FFFFFFFFFFFFFFFFFFFFFFFFFFF
IIIIIIIIIIIIIIIIIIIIIIIIICCCCCCCCCCCCCCCCCCCCCCCCCCCbEEbEEb EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEFFFFFFFFFFFFFFFFFFFFFFFFF

BBBBBBBBBBBBBBBBBBBBBBBBB
BBBBBBBBBBBBBBBBBBBBBBBBBBB
> print
由使用的缓冲策略决定。


I've seen on various mailing lists and forums that people keep mentioning that the print function in Python 3 is thread safe. From my own testing, I see no reason to doubt that.

import threading
import time
import random

def worker(letter):
    print(letter * 50)


threads = [threading.Thread(target=worker, args=(let,)) for let in "ABCDEFGHIJ"]
for t in threads:
    t.start()
for t in threads:
    t.join()

When I run it with Python 3, even though some of the lines may be out of order, they are still always on their own lines. With Python 2, however, the output is fairly sporadic. Some lines are joined together or indented. This is also the case when I from __future__ import print_function

I'm just trying to understand WHY this is the case?

解决方案

For Python 3.7: The print() function is a builtin, it by default sends output to sys.stdout, the documentation of which says, among other things:

When interactive, stdout and stderr streams are line-buffered. Otherwise, they are block-buffered like regular text files. You can override this value with the -u command-line option.

So its really the combination of interactive mode and sys.stderr that is responsible for the behaviour of the print function as demonstrated in the example.

And we can get closer to the truth if the worker function in your example program is changed to

def worker(letter):
    print(letter*25, letter*25, sep='\n')

then we get outputs similar to the one below, which clearly shows that print in itself is not thread safe, what you can expect is that individual lines do not get interleaved with each other.

DDDDDDDDDDDDDDDDDDDDDDDDDJJJJJJJJJJJJJJJJJJJJJJJJJ

JJJJJJJJJJJJJJJJJJJJJJJJJ
DDDDDDDDDDDDDDDDDDDDDDDDDGGGGGGGGGGGGGGGGGGGGGGGGG
GGGGGGGGGGGGGGGGGGGGGGGGGAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAHHHHHHHHHHHHHHHHHHHHHHHHH
HHHHHHHHHHHHHHHHHHHHHHHHH


FFFFFFFFFFFFFFFFFFFFFFFFF
IIIIIIIIIIIIIIIIIIIIIIIIICCCCCCCCCCCCCCCCCCCCCCCCC
CCCCCCCCCCCCCCCCCCCCCCCCC
IIIIIIIIIIIIIIIIIIIIIIIII

EEEEEEEEEEEEEEEEEEEEEEEEE

EEEEEEEEEEEEEEEEEEEEEEEEEFFFFFFFFFFFFFFFFFFFFFFFFF

BBBBBBBBBBBBBBBBBBBBBBBBB
BBBBBBBBBBBBBBBBBBBBBBBBB

So ultimately thread safety of print is determined by the buffering strategy used.

这篇关于是什么使Python3的打印函数线程安全?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆