使用line_profiler进行Python评测-动态删除@profile语句的聪明方法?

使用line_profiler进行Python评测-动态删除@profile语句的聪明方法?,python,profiling,decorator,python-decorators,Python,Profiling,Decorator,Python Decorators,我想用优秀的,但只是一些时间。为了让它发挥作用,我添加了 @profile 在每次函数调用之前,例如 @profile def myFunc(args): blah return 执行 kernprof.py -l -v mycode.py args 但是我不想每次都要手工输入@profile装饰器,因为大多数时候我都希望在没有它们的情况下执行代码,如果我试图包含它们,就会出现异常,例如 mycode.py args 有没有一种快乐的媒介,可以让我根据某个条件开关/参数动

我想用优秀的,但只是一些时间。为了让它发挥作用,我添加了

@profile
在每次函数调用之前,例如

@profile
def myFunc(args):
    blah
    return
执行

kernprof.py -l -v mycode.py args
但是我不想每次都要手工输入
@profile
装饰器,因为大多数时候我都希望在没有它们的情况下执行代码,如果我试图包含它们,就会出现异常,例如

mycode.py args
有没有一种快乐的媒介,可以让我根据某个条件开关/参数动态地删除装饰器,而不必手动操作和/或过多地修改每个函数?

与其删除
@profile
装饰器行,不如提供您自己的直通无操作版本

您可以将以下代码添加到项目的某个位置:

try:
    # Python 2
    import __builtin__ as builtins
except ImportError:
    # Python 3
    import builtins

try:
    builtins.profile
except AttributeError:
    # No line profiler, provide a pass-through version
    def profile(func): return func
    builtins.profile = profile
在使用
@profile
装饰器导入任何代码之前导入此代码,您可以在线条分析器处于活动状态或不处于活动状态的情况下使用该代码

因为虚拟装饰器是一个传递函数,所以执行性能不会受到影响(只有导入性能受到的影响很小)

如果你不喜欢搞乱内置程序,你可以把它作为一个单独的模块;说
profile\u support.py

try:
    # Python 2
    import __builtin__ as builtins
except ImportError:
    # Python 3
    import builtins

try:
    profile = builtins.profile
except AttributeError:
    # No line profiler, provide a pass-through version
    def profile(func): return func

(不分配给
内置.profile
)并在任何使用
@profile
装饰器的模块中使用
从profile\u支持导入profile

我在Python 3.4中使用以下修改版本

try:
    import builtins
    profile = builtins.__dict__['profile']
except KeyError:
    # No line profiler, provide a pass-through version
    def profile(func): return func

一条评论逐渐成为@Martijin Pieters答案的变体

我宁愿不涉及
\uuuuuuuuuuuuuuu
。如果没有评论,其他人几乎不可能猜测到
line\u profiler
,而事先不知道这一点

查看
kernprof
,实例化
LineProfiler
就足够了

try:
    from line_profiler import LineProfiler
    profile = LineProfiler()
except ImportError:
    def profile(func):
        return func
导入(显式)而不是全局修改内置的
(隐式)。如果分析装饰器是永久性的,那么它们的来源应该在代码本身中是明确的


在有
line\u profiler
的情况下,无论是否由
kernprof
运行,上述方法都会在每次运行时使用profiler包装修饰过的函数。这种副作用可能是不希望出现的。

您根本不需要导入
\uuuuuuuuuu内置文件
/
内置文件
LineProfiler
,在尝试查找
配置文件时,您只需依靠
名称错误

try:
    profile
except NameError:
    profile = lambda x: x

但是,这需要包含在每个使用
profile
的文件中,但它不会(永久)改变Python的全局状态(内置)。

我会问自己,我是否真的需要如此频繁地进行profile,以至于它需要这样的支持。我不是说你做或不做,所以你不必回答。我刚刚发现这个用例有点令人惊讶。代码需要很长时间(目前需要几个小时…)才能执行,所以现在我想一举两得,同时获得结果和分析。我想我将评测视为一个正在进行的过程(因为我对它不熟悉/很兴奋),所以我不会在(许多)函数中使用它,声明它已完成并删除所有的装饰程序。我不会让一些事情花费数小时。它不需要花费任何费用,并且准确地告诉您发生了什么。@jtlz2您还可以将函数和类方法包装到概要文件中(可能在单独的概要文件脚本中),并避免完全按照此处所述添加
@profile
装饰程序()。