我写了这个小测试类,基于 a Python issue - closed/fixed ,它似乎发生在 Fedora 15 上的 Python 2.7.1 中。
from subprocess import Popen, PIPE
from threading import Thread
OUTPUT = "asl;dkfhqwiouethnjzxvnhsldfhuyasdhofuiweqamchuisemfawepfhuaipwemhfuaehfclkuehnflw ehfcoiuwehfiuwmhefuiwehfoiuhSfcl hfulh fuiqhuif huiwafh uiahf iUH fhh flkJH fl HASLFuhSAIULFhSUA HFulSAHfOI SUFChiuwqhncriouweycriuowanbyoUIWCryu iWyruawyrouiWYRcoiu YCRoiuNr uyr oUIAWryocIUWRNyc owuroiuNr cuWyrnawueitcnoy U IuiR yiuowaYnorc oWIUAr coiury iuoAW rnuoi asdfsdfd\n"
class X(Thread):
def __init__(self):
Thread.__init__(self)
def run(self):
print("Running")
for i in xrange(10):
s = Popen(
"cat /tmp/junk",
shell=True,
stdout=PIPE,
universal_newlines=True
)
output = s.communicate()[0]
if not output == OUTPUT:
print("Error: %r" % output)
XThreads = set([])
for i in xrange(1000):
XThreads.add(X())
for x in XThreads:
x.start()
只需创建一个文件,在本例中为/tmp/junk,其中包含 OUTPUT
的内容,减去最后一个换行符。
运行它,您会期望在每一行看到“Running”。但是,有时会显示“Running”或“RunningRunning\n\nRunning”。
(删除了对实际问题的引用,因为这是一个错误的症状,感谢@phihag 的回答)。
实际问题:https://stackoverflow.com/questions/9338409/python-subprocess-popen-corrupts-binary-streams
最佳答案
您看到的行为与子流程无关;我可以重现它:
import threading
def run(): print("Running")
for x in [threading.Thread(target=run) for i in range(1000)]:
x.start()
这是因为Python's print
is not thread-safe .为避免打印文本和换行符之间的竞争条件,直接写入标准输出,如下所示:
import threading,sys
def run(): sys.stdout.write("Running\n")
for x in [threading.Thread(target=run) for i in range(1000)]:
x.start()
这假设对 stdout 的底层 write
调用是线程安全的。 That depends on the platform .
关于python - subprocess.Popen 不是线程安全的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9337711/