Python and Design Mode--Decorator Mode

Original Link: https://yq.aliyun.com/articles/70737

1. Fast food system (3)

That fast-food meal system was mentioned again, but today we're only going to feature one of these categories: beverages.First, recall the beverages:

class Beverage():
    name = ""
    price = 0.0
    type = "BEVERAGE"
    def getPrice(self):
        return self.price
    def setPrice(self, price):
        self.price = price
    def getName(self):
        return self.name


class coke(Beverage):
    def __init__(self):
        self.name = "coke"
        self.price = 4.0


class milk(Beverage):
    def __init__(self):
        self.name = "milk"
        self.price = 5.0

In addition to basic configuration, fast-food restaurants can choose to add ice when they sell cola, or 0.3 yuan if they add ice, or 0.5 yuan if they sell milk or 0.5 yuan if they add sugar.How can I solve this problem?Decorator mode can be chosen to solve this type of problem.First, define the decorator class:

class drinkDecorator():
    def getName(self):
        pass
    def getPrice(self):
        pass

class iceDecorator(drinkDecorator):
    def __init__(self,beverage):
        self.beverage=beverage
    def getName(self):
        return self.beverage.getName()+" +ice"
    def getPrice(self):
        return self.beverage.getPrice()+0.3
    
class sugarDecorator(drinkDecorator):
    def __init__(self,beverage):
        self.beverage=beverage
    def getName(self):
        return self.beverage.getName()+" +sugar"
    def getPrice(self):
        return self.beverage.getPrice()+0.5

Once the decorators are built, they can be associated with beverages in specific business scenarios.Take Coke+Ice as an example, and the sample business scenario is as follows:

if  __name__=="__main__":
    coke_cola=coke()
    print "Name:%s"%coke_cola.getName()
    print "Price:%s"%coke_cola.getPrice()
    ice_coke=iceDecorator(coke_cola)
    print "Name:%s" % ice_coke.getName()
    print "Price:%s" % ice_coke.getPrice()

The printout is as follows:
Name:coke
Price:4.0
Name:coke +ice
Price:4.3

2. Decorator Mode

The decorator pattern is defined as follows: dynamically add some extra responsibility to an object.Decorator mode is more flexible in increasing functionality than generating subclasses.

The decorator mode is very similar to the proxy mode mentioned in the previous section. It can be thought that the decorator mode is a special application of the proxy mode. Both have the same interface. The difference is that they focus on controlling the process of the theme class, while the decorator mode focuses on strengthening or weakening the function of the class.
Last time, the dynamic proxy model in JAVA was an important means to implement AOP.In Python, AOP is simpler and more convenient through the decorator mode.
Let's first explain what AOP is.AOP, Aspect Oriented Programming, translated in Chinese as facet-oriented programming, can be interpreted as: if there are repetitive operation behaviors in several or more logical processes (such logical processes may be located in different objects and interfaces), they can be extracted (i.e., formed)Section), for unified management and maintenance.For example, if the system needs to print logs everywhere, the operation of printing logs can be extracted and maintained as facets.
From the point of view of the relationship between programming thought, AOP and OOP (object-oriented programming) can be considered as side-by-side relationship, which can be replaced or combined.In fact, decorators are naturally supported in Python, as in the following example:

def log(func):
    def wrapper(*args, **kw):
        print 'call %s():' % func.__name__
        return func(*args, **kw)
    return wrapper

@log
def now():
    print '2016-12-04'
if  __name__=="__main__":
    now()

Print as follows:
call now():
2016-12-04
The log interface is the definition of the decorator, while Python's @ grammar section directly supports the use of the decorator.
If you want to print logs in the fast food system, how do you make the AOP transformation?It can be implemented by static or class methods of classes:

class LogManager:
    @staticmethod
    def log(func):
        def wrapper(*args):
            print "Visit Func %s"%func.__name__
            return func(*args)
        return wrapper

Print the accessed log information directly @LogManager.log where you need to print the log.For example, if @LogManager.log is added before the beverage class function and the scene class remains unchanged, the printout will be as follows:
Visit Func getName
Name:coke
Visit Func getPrice
Price:4.0
Visit Func getName
Name:coke +ice
Visit Func getPrice
Price:4.3

3. Advantages and scenarios of decorator mode

Advantage:
1. Decorator mode is an alternative to inheritance mode, which can lightly expand the function of the decorated object;
2. Python's decorator mode is a way to implement AOP, which facilitates the unified management of the same operation at different call locations.
Scenarios:
1. The functions of a class need to be extended, enhanced, or weakened, as in this case.

4. Disadvantages of Decorator Mode

1. It is difficult to debug and maintain the multi-layer decorator.

Keywords: Programming Python Java

Added by redking on Fri, 16 Aug 2019 04:16:35 +0300