2014-10-17 20 views
4

我最小的例子是使Python的`warnings.warn()`不提自己

#!/usr/bin/python3 

import warnings 

warnings.warn('Run Forest run!', stacklevel=2) 
warnings.warn('Run Forest run!') 

,它将输出

sys:1: UserWarning: Run Forest run! 
./file.py:6: UserWarning: Run Forest run! 
    warnings.warn('Run Forest run!') 

第一行给我一点信息。第二行是完美的,给我的源文件和行号......但我想摆脱冗余的第三行。那可能吗?

回答

4

原来这可能让warnings.warn()收集所有的信息,只是costumize相关信息被打印方式:

#!/usr/bin/python3 

import warnings 

def warning_on_one_line(message, category, filename, lineno, file=None, line=None): 
    return '%s:%s: %s: %s\n' % (filename, lineno, category.__name__, message) 

warnings.formatwarning = warning_on_one_line 

warnings.warn('Run Forest run!', stacklevel=2) 
warnings.warn('Run Forest run!') 

输出:

sys:1: UserWarning: Run Forest run! 
./file.py:15: UserWarning: Run Forest run! 

来源:Python module of the week

4

您得到“冗余”行的原因是因为如果您不提供stacklevel参数,则默认stacklevel为1,这基本上告诉用户警告源于的确切代码行,即您的警告功能请致电warnings.warn('Run Forest Run!')

如果您对其功能的使用方式不满意,可以使用warnings.warn_explicit()函数对其进行自定义。

https://docs.python.org/3.1/library/warnings.html#available-functions

2

如果你想捕捉异常/错误,并希望同时看到您的自定义警告消息,并且回溯,你可能更愿意使用traceback.print_exc():

import traceback 
import warnings 

def _formatwarning(msg, *a): 
    try: 
     traceback.print_exc() 
    except: 
     pass 
    return str(msg) 

warnings.formatwarning = _formatwarning 

这将使警告(”你的消息“)打印回溯,而不提及警告()本身的调用。

UPDATE:上的Python 3.6,你需要的函数签名改为:

def _formatwarning(message, category, filename, lineno, line='')