首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >python装饰器是否严格实现装饰器模式?

python装饰器是否严格实现装饰器模式?
EN

Stack Overflow用户
提问于 2011-12-14 21:05:44
回答 3查看 759关注 0票数 3

我参加了一个关于装饰器模式的会议,其中提供的大多数示例都是在java.For实例中提供的,在下面的示例中,披萨对象是用两个浇头装饰的。

代码语言:javascript
复制
Pizza vegPizza = new ToppingsType1(new ToppingType2(new Pizza()))

在python中,我已经看到装饰器在如下场景中使用

代码语言:javascript
复制
@applyTopping2
@applyTopping1
makePizza():
    pass

虽然在这里我可以看到makePizza函数被装饰了两个函数,但它与java的基于类的方法有很大的不同。我的问题是,python装饰器是严格实现装饰器模式,还是实现有点不同,但想法是一样的。

PS:我不确定在哪里可以找到装饰器的标准定义,维基百科用动态语言(JS)给出了一个例子,但我的问题仍然有效:)

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2011-12-14 21:12:59

你应该使用read this,它解释了什么是python的装饰器。

对于

,我们所说的“装饰器”和DecoratorPattern并不完全是一回事……Python修饰器是对Python语法的特定更改,它允许我们更方便地更改函数和方法(未来版本中可能还有类)。这支持更具可读性的DecoratorPattern应用程序,但也支持其他用途。

因此,您将能够使用python的装饰器实现“经典的”装饰器模式,但是您将能够使用这些装饰器做更多的事情(有趣;)。

在您的示例中,它可能如下所示:

代码语言:javascript
复制
def applyTopping1(functor):
    def wrapped():
        base_pizza = functor()
        base_pizza.add("mozzarella")
        return base_pizza
    return wrapped

def applyTopping2(functor):
    def wrapped():
        base_pizza = functor()
        base_pizza.add("ham")
        return base_pizza
    return wrapped

然后你会得到一杯玛格丽塔酒:)

票数 2
EN

Stack Overflow用户

发布于 2011-12-14 21:24:08

这不是一个真正的答案,只是一个有趣的例子,说明了如何使用Python来做事情--与静态语言相比:

代码语言:javascript
复制
def pizza_topping_decorator_factory(topping):
    def fresh_topping_decorator(pizza_function):
        def pizza_with_extra_topping(*args, **kw):
            return pizza_function(*args, **kw) + ", " + topping
        return pizza_with_extra_topping
    return fresh_topping_decorator


mozzarela = pizza_topping_decorator_factory("mozarella")
anchove = pizza_topping_decorator_factory("anchove")

@anchove
@mozzarela
def pizza():
    return "Pizza"

将此代码粘贴到Python控制台时:

代码语言:javascript
复制
>>> 
>>> print pizza()
Pizza, mozarella, anchove
票数 1
EN

Stack Overflow用户

发布于 2011-12-14 21:24:57

Python语言中的@decorator语法只不过是语法糖。

代码

代码语言:javascript
复制
@decorator
def foo():
    pass

只不过是

代码语言:javascript
复制
def foo():
    pass

foo = decorator(foo)

最终的结果取决于你想要它是什么。

您可以使用类作为decorator,并使用foo作为__init__ arg从这个类中实例化对象。

您可以使用实例化的对象作为装饰器,如下面的代码所示

代码语言:javascript
复制
class Decorator(object):
    def __init__(self, arg1, arg2):
        pass

    def __call__(self, foo):
        return foo()

@Decorator(arg1_value, arg2_value)
def foo():
    pass

这只有你自己决定你的代码看起来像什么,它将做什么,而不是任何模式或来自java世界的人:)

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8504969

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档