鱼C论坛

 找回密码
 立即注册
查看: 2305|回复: 3

[已解决]046讲装饰器相关问题

[复制链接]
发表于 2022-11-22 10:11:06 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
小甲鱼046讲布置到延长输出结果时间的一道题,要求修改以下代码,使其一秒钟输出一个结果,原代码如下:
import time
   
def fib():
    back1, back2 = 0, 1
    def func():
        nonlocal back1, back2
        back1, back2 = back2, back1 + back2
        print(back1, end=' ')
    return func
   
def get_fib(n):
    f = fib()
    for i in range(n):
        f()
   
n = int(input("请输入需要获取的斐波那契数:"))
get_fib(n)



添加延长时间的代码只需要time.sleep(1)就可以了
我们在前面加一个代码:
def delay(func):
     def call_func():
          time.sleep(1)
          func()
    return call_func

然后,小甲鱼在def func()的位置写了@dalay
我尝试着在def fib()那里写@delay,python报错了,告诉我当它试图call func()的时候,发现func是none type因此不能call
为什么会这样?所以说如果是嵌套函数,必须得是内部函数才可以用装饰器吗?
提前感谢大佬们解答!!!!
最佳答案
2022-11-22 11:03:06
本帖最后由 jackz007 于 2022-11-22 11:36 编辑

        之所以不能装饰 fib() 那是因为 fib() 不是一个正常函数,而是一个闭包,不会被多次调用,也不会返回我们想要的数列元素,装饰这个函数无法满足每秒输出 1 个数的要求,只要把函数 fib() 改写为正常函数就可以解决问题。
import time

def delay(func):
     def call_func(* args):
          time . sleep(1)
          return func(* args)
     return call_func

@delay
def fib(n):
    b = 0
    if n >= 0:
        a = b = 1
        for _ in range(2 , n) : a , b = b , a + b
    return b

def get_fib(n):
    for i in range(1 , n + 1):
        print(fib(i))
    
n = int(input("请输入需要获取的斐波那契数:"))
get_fib(n)
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2022-11-22 10:15:18 | 显示全部楼层
对不起家人们!不是在call func()的时候报错,是在f=fib()那里报错了QAQ,期待解答
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-11-22 10:26:18 | 显示全部楼层
星夕ING 发表于 2022-11-22 10:15
对不起家人们!不是在call func()的时候报错,是在f=fib()那里报错了QAQ,期待解答

将 print(back1, end=' ')  改成 return back1 试一下
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

发表于 2022-11-22 11:03:06 | 显示全部楼层    本楼为最佳答案   
本帖最后由 jackz007 于 2022-11-22 11:36 编辑

        之所以不能装饰 fib() 那是因为 fib() 不是一个正常函数,而是一个闭包,不会被多次调用,也不会返回我们想要的数列元素,装饰这个函数无法满足每秒输出 1 个数的要求,只要把函数 fib() 改写为正常函数就可以解决问题。
import time

def delay(func):
     def call_func(* args):
          time . sleep(1)
          return func(* args)
     return call_func

@delay
def fib(n):
    b = 0
    if n >= 0:
        a = b = 1
        for _ in range(2 , n) : a , b = b , a + b
    return b

def get_fib(n):
    for i in range(1 , n + 1):
        print(fib(i))
    
n = int(input("请输入需要获取的斐波那契数:"))
get_fib(n)
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-9-25 13:16

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表