首页   注册   登录
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐学习书目
Learn Python the Hard Way
Python 学习手册
Python Cookbook
Python 基础教程
Python Sites
PyPI - Python Package Index
http://www.simple-is-better.com/
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
V2EX  ›  Python

Python 装饰器使用场景疑问

  •  
  •   superbai · 68 天前 · 1043 次点击
    这是一个创建于 68 天前的主题,其中的信息可能已经有所发展或是发生改变。

    背景:一个脚本里有 2 个函数,里面都执行了比较危险的操作(删除数据),所以我想在执行前加一个确认的动作。打算用装饰器来实现,但是把装饰器加到 2 个函数上之后,执行一个函数需要确认两次...网上搜索了下,装饰器不是随着函数调用执行的。所以这种问题应该用装饰器解决么,还是我使用的姿势不对? 样例代码:

    def confirm(func):
    	def wrapper():
        	# do confirm action
            return func
        return wrapper()
        
    
    @confirm
    def delete_1():
    	# do something
    
    
    @confirm
    def delete_2():
    	# do something
        
        
    if __name__ == '__main__':
    	delete_1()
    

    这种场景下,confirm action 会执行两次

    11 回复  |  直到 2019-08-07 12:58:22 +08:00
        1
    fzzff   68 天前   ♥ 1
    装饰器最终返回一个函数引用,你的返回值就不对
        2
    Tracy1997   68 天前   ♥ 1
    return wrapper
        3
    Takamine   68 天前
    感觉用切面做这个感觉不太合适还是在这两个方法前面再抽一层出来做确认功能吧。
        4
    Takamine   68 天前   ♥ 1
    @Takamine 直接把要运行的函数当参数丢进去。
        5
    superbai   68 天前
    @fzzff #1
    @Tracy1997 #2 感谢,已经可以了~~太粗心了
        6
    superbai   68 天前
    @Takamine #4 那感觉和装饰器一样....?
        7
    frostming   68 天前   ♥ 1
    def confirm(func):
    def wrapper():
    # do confirm action
    return func()
    return wrapper

    你装饰器的返回搞错了
        8
    sikariba   68 天前   ♥ 1
    def confirm(func):
    def wrapper():
    user_input = input('yes or no?')
    if user_input == 'yes':
    return func()
    return wrapper


    @confirm
    def delete_1():
    print('delete 1')


    @confirm
    def delete_2():
    print('delete 2')


    if __name__ == '__main__':
    delete_1()
        9
    Takamine   68 天前
    @superbai 嗯阿,实现上差不多,只是自己拿业务做个代理,不用注解,呸,装饰器。
        10
    vkhsyj   68 天前   ♥ 1
    装饰器应该返回的是装饰函数,也就是你的 wrapper, 你这样返回 wrapper()的结果, 等于在脚本运行时就会需要确认,而不是在你函数调用时确认了
        11
    superbai   67 天前
    @Takamine #9 哈哈,我也是总想着注解,写装饰器写起来不太适应😂
    @vkhsyj #10 感谢,对装饰器理解不深,搞错了。
    关于   ·   FAQ   ·   API   ·   我们的愿景   ·   广告投放   ·   感谢   ·   实用小工具   ·   4362 人在线   最高记录 5043   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.3 · 23ms · UTC 03:17 · PVG 11:17 · LAX 20:17 · JFK 23:17
    ♥ Do have faith in what you're doing.