>백엔드 개발 >PHP 튜토리얼 >PHP 디자인 패턴 데코레이터 패턴

PHP 디자인 패턴 데코레이터 패턴

高洛峰
高洛峰원래의
2016-11-21 15:13:031153검색

개념

데코레이터 패턴을 사용하면 구조를 변경하지 않고도 기존 개체에 새로운 기능을 추가할 수 있습니다. 이러한 유형의 디자인 패턴은 기존 클래스를 감싸는 래퍼 역할을 하는 구조적 패턴입니다.

이 패턴은 클래스 메소드 시그니처의 무결성을 유지하면서 원래 클래스를 래핑하고 추가 기능을 제공하는 데코레이션 클래스를 만듭니다.

UML 다이어그램

PHP 디자인 패턴 데코레이터 패턴

Role

추상 구성 요소 역할(Component): 추가를 허용할 준비가 된 개체를 표준화하기 위해 개체 인터페이스를 정의합니다. 책임 즉, 이러한 객체에 책임을 동적으로 추가할 수 있습니다.

ConcreteComponent: 데코레이터는 기능을 추가하기 위해 장식할 클래스를 정의합니다. 이 클래스의 개체에 몇 가지 책임을 추가할 수 있습니다

추상 데코레이터(Decorator): 구성 요소 구성 요소 개체를 가리키는 인스턴스를 유지하고 추상 구성 요소 역할 구성 요소 인터페이스와 일치하는 인터페이스를 정의합니다

콘크리트 데코레이터 역할(ConcreteDecorator): 구성 요소에 책임을 추가합니다.

적용 가능한 시나리오

객체에 동적으로 기능을 추가해야 하며, 이러한 기능은 동적으로 취소될 수 있습니다.

일부 기본 기능의 순열과 조합으로 생성되는 매우 많은 기능을 추가해야 하므로 상속관계가 비현실적입니다.

하위 클래스 생성 방법을 확장에 사용할 수 없는 경우. 어떤 경우에는 독립적인 확장이 많이 있을 수 있으며, 각 조합을 지원하기 위해 많은 수의 하위 클래스가 생성되어 하위 클래스 수가 폭발적으로 증가하게 됩니다. 또 다른 경우는 클래스 정의가 숨겨져 있거나 클래스 정의를 사용하여 하위 클래스를 생성할 수 없기 때문일 수 있습니다.

코드

<?php
header(&#39;Content-type:text/html;charset=utf-8&#39;);

/**
 * 装饰器模式
 */

/**
 * Interface IComponent 组件对象接口
 */
interface IComponent
{
    public function display();
}

/**
 * Class Person 待装饰对象
 */
class Person implements IComponent
{
    private $_name;

    /**
     * Person constructor. 构造方法
     *
     * @param $name 对象人物名称
     */
    public function __construct($name)
    {
        $this->_name = $name;
    }

    /**
     * 实现接口方法
     */
    public function display()
    {
        echo "装扮者:{$this->_name}<br/>";
    }
}

/**
 * Class Clothes 所有装饰器父类-服装类
 */
class Clothes implements IComponent
{
    protected $component;

    /**
     * 接收装饰对象
     *
     * @param IComponent $component
     */
    public function decorate(IComponent $component)
    {
        $this->component = $component;
    }

    /**
     * 输出
     */
    public function display()
    {
        if(!empty($this->component))
        {
            $this->component->display();
        }
    }

}


/**
 * 下面为具体装饰器类
 */

/**
 * Class Sneaker 运动鞋
 */
class Sneaker extends Clothes
{
    public function display()
    {
        echo "运动鞋  ";
        parent::display();
    }
}

/**
 * Class Tshirt T恤
 */
class Tshirt extends Clothes
{
    public function display()
    {
        echo "T恤  ";
        parent::display();
    }
}

/**
 * Class Coat 外套
 */
class Coat extends Clothes
{
    public function display()
    {
        echo "外套  ";
        parent::display();
    }
}

/**
 * Class Trousers 裤子
 */
class Trousers extends Clothes
{
    public function display()
    {
        echo "裤子  ";
        parent::display();
    }
}


/**
 * 客户端测试代码
 */
class Client
{
    public static function test()
    {
        $zhangsan = new Person(&#39;张三&#39;);
        $lisi     = new Person(&#39;李四&#39;);

        $sneaker  = new Sneaker();
        $coat     = new Coat();

        $sneaker->decorate($zhangsan);
        $coat->decorate($sneaker);
        $coat->display();

        echo "<hr/>";

        $trousers = new Trousers();
        $tshirt   = new Tshirt();

        $trousers->decorate($lisi);
        $tshirt->decorate($trousers);
        $tshirt->display();
    }
}

Client::test();

실행 결과:

코트, 운동화, 드레서: 장산
티셔츠, 바지, 드레서: 리시


성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.