有几种方法可以写入stderr:

print >> sys.stderr, "spam"  # Python 2 only.

sys.stderr.write("spam\n")

os.write(2, b"spam\n")

from __future__ import print_function
print("spam", file=sys.stderr)

这些方法之间有什么区别?应首选哪种方法?


当前回答

如果进行简单测试:

import time
import sys

def run1(runs):
    x = 0
    cur = time.time()
    while x < runs:
        x += 1
        print >> sys.stderr, 'X'
    elapsed = (time.time()-cur)
    return elapsed

def run2(runs):
    x = 0
    cur = time.time()
    while x < runs:
        x += 1
        sys.stderr.write('X\n')
        sys.stderr.flush()
    elapsed = (time.time()-cur)
    return elapsed

def compare(runs):
    sum1, sum2 = 0, 0
    x = 0
    while x < runs:
        x += 1
        sum1 += run1(runs)
        sum2 += run2(runs)
    return sum1, sum2

if __name__ == '__main__':
    s1, s2 = compare(1000)
    print "Using (print >> sys.stderr, 'X'): %s" %(s1)
    print "Using (sys.stderr.write('X'),sys.stderr.flush()):%s" %(s2)
    print "Ratio: %f" %(float(s1) / float(s2))

你会发现sys.stderr.write()总是快1.81倍!

其他回答

Python 3:

print("fatal error", file=sys.stderr)

Python 2:

print >> sys.stderr, "fatal error"

答案很长

print>>sys.stderr已在Python3中消失。http://docs.python.org/3.0/whatsnew/3.0.html说:

旧:print>>sys.stderr,“致命错误”新建:打印(“致命错误”,文件=sys.stderr)

对我们中的许多人来说,将目的地归为指挥的终点,感觉有些不自然。替代方案

sys.stderr.write("fatal error\n")

看起来更面向对象,从通用到特定都很优雅。但请注意,书写并不是打印的1:1替代。

EDIT在事后看来,我认为更改sys.stderr和没有看到行为更新可能会产生混淆,这使得这个答案不如其他人指出的那样简单。

使用partial只会节省1行代码。潜在的混淆不值得保存一行代码。

起初的

为了更简单,这里有一个使用“partial”的版本,这对包装函数有很大帮助。

from __future__ import print_function
import sys
from functools import partial

error = partial(print, file=sys.stderr)

然后你就这样使用它

error('An error occured!')

您可以通过执行以下操作(从http://coreygoldberg.blogspot.com.au/2009/05/python-redirect-or-turn-off-stdout-and.html):

# over-ride stderr to prove that this function works.
class NullDevice():
    def write(self, s):
        pass
sys.stderr = NullDevice()

# we must import print error AFTER we've removed the null device because
# it has been assigned and will not be re-evaluated.
# assume error function is in print_error.py
from print_error import error

# no message should be printed
error("You won't see this error!")

这样做的缺点是在创建时将sys.stderr的值部分分配给包装函数。这意味着,如果稍后重定向stderr,则不会影响此函数。如果您计划重定向stderr,请使用aaguirre在本页中提到的**kwargs方法。

如果进行简单测试:

import time
import sys

def run1(runs):
    x = 0
    cur = time.time()
    while x < runs:
        x += 1
        print >> sys.stderr, 'X'
    elapsed = (time.time()-cur)
    return elapsed

def run2(runs):
    x = 0
    cur = time.time()
    while x < runs:
        x += 1
        sys.stderr.write('X\n')
        sys.stderr.flush()
    elapsed = (time.time()-cur)
    return elapsed

def compare(runs):
    sum1, sum2 = 0, 0
    x = 0
    while x < runs:
        x += 1
        sum1 += run1(runs)
        sum2 += run2(runs)
    return sum1, sum2

if __name__ == '__main__':
    s1, s2 = compare(1000)
    print "Using (print >> sys.stderr, 'X'): %s" %(s1)
    print "Using (sys.stderr.write('X'),sys.stderr.flush()):%s" %(s2)
    print "Ratio: %f" %(float(s1) / float(s2))

你会发现sys.stderr.write()总是快1.81倍!

如果由于严重错误而要退出程序,请使用:

sys.exit("Your program caused a fatal error. ... description ...")

并在标头中导入sys。

这将模拟标准打印函数,但输出到stderr

def print_err(*args):
    sys.stderr.write(' '.join(map(str,args)) + '\n')