【问题标题】:The function has been called 10 times but the decorator has only been called once. Why?该函数被调用了 10 次,但装饰器只被调用了一次。为什么?
【发布时间】:2019-02-22 21:41:21
【问题描述】:
def call_counter(func):
    print('Called\n')
    def helper(x):
        helper.calls+=1
        return func(x)
    helper.calls=0
    return helper

@call_counter
def succ(x):
    return x+1

print(str(succ.calls)+'\n')
for i in range(10):
    print(succ.calls)
    succ(i)
print('\n')
print(succ.calls)

【问题讨论】:

  • 这里是python新手
  • 我不明白你在问什么。您的代码输出正是我所期望的。您能否在您期望什么以及为什么的问题上提供更多解释?也许显示你得到的输出以及你期望得到的结果?
  • 我不明白为什么装饰器只在函数上调用一次。它应该被调用 10 次,对吧?循环中的每次迭代一次,因此“Called”应打印 10 次。我错过了什么?

标签: python-3.x python-decorators


【解决方案1】:

你评论了:

我不明白为什么装饰器只在函数上调用一次。它应该被调用 10 次,对吗?循环中的每次迭代一次,因此“Called”应打印 10 次。我错过了什么?

我认为您将装饰器的运行与包装函数的运行混淆(在您的代码中命名为 helper)。装饰器只被调用一次,当它通过原始函数并返回包装函数时,它被存储为 succ 在你的模块中。包装器是你的循环调用十次的东西。

当我运行你的代码时,这是我得到的输出:

Called

0

0
1
2
3
4
5
6
7
8
9


10

只有前两行(“Called”和后面的空行)来自装饰器调用。如果只运行函数定义而不运行循环,则可以看到这一点。即使您根本没有调用该函数,您也会立即看到“Called”打印出来。

顶部的零和底部的十来自您在顶层的print 语句。紧挨着打印的数字是循环的输出,它会在每次对包装函数进行新调用之前打印先前调用的计数。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-11-24
    • 1970-01-01
    • 2013-12-11
    • 2013-11-20
    • 2019-10-02
    • 1970-01-01
    相关资源
    最近更新 更多