PHP Design Patterns Decorator

PHP Design Patterns Decorator

Factory model come to an end, let's examine some other models. I do not know women's heavyweights have not tried? Women chiefs said that many programmers yo. In fact, today the decorator pattern on it and makeup like. I believe that if there is a program in Yuan MM, then, and you can immediately make it clear that design patterns.

Gof class diagram and explanations

Decorative word, Let us put him into makeup. First you have to have a face, then base, then on the makeup, makeup can be a morning to go to work, you can work when heavy makeup to fill out Hi. Of course, farmers are code point in time off work just to catch the second half of the night games. Anyway, no matter how makeup, your face or your face, there may be another person into someone else does not know, but this is indeed your face. This is the decorator of objects (faces) various decorative (make-up), so that the face look better (increased duties).

GoF Definition: dynamically add additional responsibilities to an object, for increased functionality, Decorator pattern generation more flexible than subclass

FIG class GoF

 

 

Code
interface Component{
    public function operation();
}

class ConcreteComponent implements Component{
    public function operation(){
        echo "I'm face!" . PHP_EOL;
    }
}

A very simple interface and a realization, where we put a specific category seen as a face it!

abstract class Decorator implements Component{
    protected $component;
    public function __construct(Component $component){
        $this->component = $component;
    }
}

Abstract decorator class that implements the Component interface, but does not implement operation () method, so that subclasses to achieve. Here the main Componet save a reference to a will is necessary for him to decorate. Corresponds to a specific class above, we are ready to face make-up to it!

class ConcreteDecoratorA extends Decorator{
    public $addedState = 1; // 没什么实际意义的属性,只是区别于ConcreteDecoratorB

    public function operation(){
        echo $this->component->operation() . "Push " . $this->addedState . " cream!" . PHP_EOL;
    }
}
class ConcreteDecoratorB extends Decorator{
    public function operation(){
        $this->component->operation();
        $this->addedBehavior();
    }

    // 没什么实际意义的方法,只是区别于ConcreteDecoratorA
    public function addedBehavior(){
        echo "Push 2 cream!" . PHP_EOL;
    }
}

Two specific decorators. Here I painted cream twice, after all, is a pure man, to makeup this thing really do not understand. The first step should first like foundation to fight, right? But this way, we both realized decorator is to face two coats of cream.

  • As can be seen from the code, we have been the specific target of the ConcreteComponent to packaging
  • Further down, then we are in fact on his operation () This method wraps twice, each time the previous plus a little something on the basis of
  • Do not struggle with added properties and methods on the A and B decorators, they just GoF class diagram is used to distinguish the two decorators not the same thing, every decorator can do a lot of other things, Component Object not only a certain operation () this way, we can all go selectively decorative object or part of the method
  • We seem to have inherited Component, a direct subclass does not rewrite all the way on the line, do this effortlessly doing? Pro, understand the concept of a combination of lower yo, we Decorator parent class is a reference to a real object, oh, oh decoupling itself, we only do it for real object package, you can not be directly instantiated directly with the decorator
  • Or you did not understand? Good is it? Old class system, ah, ah you dare method just change? Try this stock decorator when you want to write to a former cattle (S) force (B) code extension of new features, maybe wonders!

Phone this stuff dry, but some rice, some O, is certain, we can not play with, well, buddy phone shell to concentrate on it! Ah, I first prepared a transparent shell (Component), looks like a little ugly, no way, who told the poor man. To a meter plus a variety of solid color (DecoratorA1), then plant a variety of colors printed on the back (DecoratorB1) it; O in a recent phone looking like flow was significantly endorsement, then I will give him a cell phone with a variety of shell Bright colors (DecoratorA2) and star of the cartoon picture (DecoratorB2); the last one was, like mobile phones has begun to lead the industry, and the folding screen to hit this thing is not my business to sell mobile phone shell thing! ! Well, you do not give a brother, or with me some rice, a mixed O Go! !

The complete code: Decorator

Examples

Continue to send text messages, use the factory pattern before we solve the problem of multiple SMS operators. This time we have to solve the problem message content template. For SMS promotion classes, according to the latest advertising law, we are not a "first in the country," and, of course, some less civilized language we also can not use the kind of words, "the world's first."

The current situation is such that we have a template class before long SMS, the content of which is fixed, the old system are still using this template, the old system is facing internal staff, less demanding on the language content. The new system needs to be sent to the whole network, that is, internal and external users to be sent. At this time, we can use the decorator pattern to the packaging of the message template old system. In fact, that simple point, we are a decorator to do text replacement feature. Good is it? Of course we can not change the original template method in the class to achieve a modified extension of the old templates and other content.

FIG SMS Class

 

 

Complete source code: SMS decorator method

<?php
// 短信模板接口
interface MessageTemplate
{
    public function message();
}

// 假设有很多模板实现了上面的短信模板接口
// 下面这个是其中一个优惠券发送的模板实现
class CouponMessageTemplate implements MessageTemplate
{
    public function message()
    {
        return '优惠券信息:我们是全国第一的牛X产品哦,送您十张优惠券!';
    }
}

// 我们来准备好装饰上面那个过时的短信模板
abstract class DecoratorMessageTemplate implements MessageTemplate
{
    public $template;
    public function __construct($template)
    {
        $this->template = $template;
    }
}

// 过滤新广告法中不允许出现的词汇
class AdFilterDecoratorMessage extends DecoratorMessageTemplate
{
    public function message()
    {
        return str_replace('全国第一', '全国第二', $this->template->message());
    }
}

// 使用我们的大数据部门同事自动生成的新词库来过滤敏感词汇,这块过滤不是强制要过滤的内容,可选择使用
class SensitiveFilterDecoratorMessage extends DecoratorMessageTemplate
{
    public $bigDataFilterWords = ['牛X'];
    public $bigDataReplaceWords = ['好用'];
    public function message()
    {
        return str_replace($this->bigDataFilterWords, $this->bigDataReplaceWords, $this->template->message());
    }
}

// 客户端,发送接口,需要使用模板来进行短信发送
class Message
{
    public $msgType = 'old';
    public function send(MessageTemplate $mt)
    {
        // 发送出去咯
        if ($this->msgType == 'old') {
            echo '面向内网用户发送' . $mt->message() . PHP_EOL;
        } else if ($this->msgType == 'new') {
            echo '面向全网用户发送' . $mt->message() . PHP_EOL;
        }

    }
}

$template = new CouponMessageTemplate();
$message = new Message();

// 老系统,用不着过滤,只有内部用户才看得到
$message->send($template);

// 新系统,面向全网发布的,需要过滤一下内容哦
$message->msgType = 'new';
$template = new AdFilterDecoratorMessage($template);
$template = new SensitiveFilterDecoratorMessage($template);

// 过滤完了,发送吧
$message->send($template);
Explanation
  • The greatest benefit decorators: the contents of the original code case where one does not change the original code, scalable, open closed principle; the second is every decorator complete their function, single responsibility; third is to use a combination of Inherited feeling;
  • Ideal for: the old system to be extended
  • Be careful: too many decorators will you engage halo
  • Not necessarily be on the same method of decoration, in fact, decorators should be more of a decorative object, the object is extended here we are all decorated for the output of a method, but only for this article, decorator in fact, more extensive application
  • Features decorators are all inherited from a primary interface or classes, objects such benefits is to return the same abstract data, has the same behavior properties, otherwise, it is not before the decorative object, but a new object of
  • It does not matter a bit difficult to understand, we have this example is actually very reluctantly, this design pattern mentioned Java-I in "Head First Design Patterns" in the / O serial interface is used in this design pattern: FileInputStream, LineNumberInputStream, BufferInputStream Wait
  • Laravel framework middleware pipeline, in fact, here is a comprehensive application of a variety of modes, which also applied to the decorator pattern: Laravel HTTP - Pipeline analysis source middleware decorator pattern
  • Also in Laravel, the log processing here is also Monolog are decorated, interested students can go to find the next
Published 41 original articles · won praise 6 · views 50000 +

Guess you like

Origin blog.csdn.net/bujidexinq/article/details/104964458