laravel에서 사용되는 디자인 패턴: 팩토리 모드, 싱글톤 모드, 등록 트리 모드, 어댑터 모드, 전략 모드, 데이터 객체 매핑 모드, 관찰자 모드, 프로토타입 모드, 데코레이터 모드, 반복자 모드, 프록시 모드 등
이 글에서는 Laravel에서 일반적으로 사용되는 몇 가지 디자인 패턴을 소개합니다. . .
1: 팩토리 패턴 예: Auth::user()
여기에서 Auth
이 클래스는 팩토리의 메서드입니다. 인증
은 등록 트리의 별칭입니다. Auth::user()
此处Auth
这个类就是工厂中的方法,Auth
是注册树中的别名。
好处:
类似于函数的封装,使对象有一个统一的生成(实例化)入口。当我们对象所对应的类的类名发生变化的时候,我们只需要改一下工厂类类里面的实例化方法即可。
2:单例模式
好处:
对象不可外部实例化并且只能实例化一次,节省资源。
实现方式:
private static $ins = null; //设置私有的属性 private function __construct() {} //使外部无法new这个类 public static function getIns() { //暴露给外部的调用方法 if(self::$ins instanceof self) { return self::$ins; } else { self::$ins = new self(); return self::$ins; } }
声明一个类的私有或者保护的静态变量,构造方法声明为私有(不允许外部进行new操作),如果不存在则实例化它,然后返回,如果存在则直接返回。
3:注册树模式
使用:
config/app
里的aliases
数组便是一个注册树
好处:
注册树模式就是使用数组结构来存取对象,工厂方法只需要调用一次(可以放到系统环境初始化这样的地方),以后需要调用该对象的时候直接从注册树上面取出来即可,不需要再调用工厂方法和单例模式。
实现方法:
class Register { protected static $objects function set($alias,$object) { //将对象映射到全局树上 self::$objects[$alias]=$object; } static function get($name) { //获取对象 return self::$objects[$name]; } function _unset($alias) { //从全局树移除对象 unset(self::$onjects[$alias]); } }
$alias
表示别名,自己设定
在工厂模式中添加
Register::set(‘db1’,$db);
其他任何地方调用只需要调用注册器读取即可
Register::$objects[‘db1’];
4:适配器模式
将不同工具的不同函数接口封装成统一的API,方便调用。如:mysql
,mysqli
,PDO
。
实现:在接口类里面申明统一的方法体,再让不同的类去实现这个接口,和重写其抽象方法。
interface Database { function connect($host,$user,$password,$dbname); function query($sql); function close(); }
然后再去用不同的工具函数去实现相同的接口。
5:策略模式
好处:
将一组特定的行为和算法封装成类,以适应某些特定的上下文环境,将逻辑判断和具体实现分离,实现了硬编码到解耦,并可实现IOC、依赖倒置、反转控制。
实现:
1.定义一个策略接口文件(UserStrategy.php
),定义策略接口,声明策略
2.定义具体类(FemaleUserStrategy.php
,MaleUserStrategy.php
),实现策略接口,重写策略方法
class Page { protected $strategy; function index() { if($request->get('female')) { $strategy=new FemaleUserStrategy(); } else { $strategy=new MaleUserStrategy(); } $this->strategy->method(); } public function __construct(UserStrategy $strategy) { $this->strategy=$strategy; } }
6:数据对象映射模式
好处:将对象和数据存储映射起来,对一个对象的操作会映射为对数据存储的操作,这也是ORM的实现机制。
class Model { public $id; public $name; public $email; …… function __construct($id) { //构造函数,调用class时自动执行,用来初始化。 //查询逻辑 } function __destruct() { //析构函数,当class调用完成后自动执行,用它来销毁实例,释放资源。 //增删改逻辑 } }
7:观察者模式
使用:
触发类Event
<?php namespace App\Events; abstract class Event { //逻辑代码 }
监听类EventListener
이점:
함수 캡슐화와 유사하게 개체가 통합된 생성(인스턴스화) 입구를 가질 수 있습니다. 객체에 해당하는 클래스의 클래스 이름이 변경되면 팩토리 클래스의 인스턴스화 방법만 변경하면 됩니다.2: 싱글톤 모드
이점: 객체는 외부에서 인스턴스화할 수 없으며 한 번만 인스턴스화할 수 있으므로 리소스가 절약됩니다.
구현 방법:<?php namespace App\Listeners; use App\Events\SomeEvent; use Illuminate\Queue\InteractsWithQueue; use Illuminate\Contracts\Queue\ShouldQueue; class EventListener { /** * Create the event listener. * * @return void */ public function __construct() { // } /** * Handle the event. * * @param SomeEvent $event * @return void */ public function handle(SomeEvent $event) { // } }클래스의 비공개 또는 보호된 정적 변수를 선언하고 생성자를 비공개로 선언합니다(외부 새 작업은 허용되지 않음). 존재하지 않으면 인스턴스화하고 존재하면 반환합니다. 직접 반환. 🎜🎜3: 등록 트리 모드 🎜🎜🎜🎜🎜 사용: 🎜🎜🎜
config/app
의 aliases
배열은 등록 트리입니다. 🎜🎜🎜이점: 🎜 🎜🎜등록 트리 모드는 배열 구조를 사용하여 객체에 액세스합니다. 팩토리 메소드는 한 번만 호출하면 됩니다(시스템 환경 초기화 등의 위치에 배치할 수 있음). 등록 트리에서 직접 가져올 수 있습니다. 팩토리 메서드와 싱글톤 패턴을 호출할 필요가 없습니다. 🎜🎜🎜구현 방법: 🎜🎜$Object = new Object(); $object_1 = clone $Object; $object_2 = clone $Object;🎜
$alias
는 별칭을 나타내며 직접 설정합니다. 🎜🎜공장 모드에서 추가 🎜🎜Register::set('db1',$db);
🎜🎜다른 장소 호출은 읽기 위해 레지스터만 호출하면 됩니다🎜🎜Register::$objects['db1'];
🎜🎜🎜🎜4: 어댑터 모드🎜🎜🎜 🎜 쉽게 호출할 수 있도록 다양한 도구의 다양한 기능 인터페이스를 통합 API로 캡슐화합니다. 예: mysql
, mysqli
, PDO
. 🎜🎜구현: 인터페이스 클래스에 통합 메서드 본문을 선언한 다음 다양한 클래스에서 이 인터페이스를 구현하고 추상 메서드를 다시 작성하도록 합니다. 🎜class Method2 extends Method { function doSomething() { echo "<div style='color:red'>" parent::doSomething(); echo "</div>"; } } interfa Decorator { //定义装饰器接口 function beforeAction(); function afterAction(); //more decoratorMethod…… } class SomeClass { protected $decorators = []; function addDecorator(Decorator $decorator) { $this->decorators[] = $decorator; } function beforeMethod() { foreach ($this->decorators as $row) { $row->beforeAction(); } } function afterMethod() { $decorators = array_reverse($this->decorators); //做一个反转 foreach ($this->decorators as $row) { $row->afterAction(); } } function action() { $this->beforeMethod(); //method; $this->afterMethod(); } } class OneDecorator implements Decorator { protected $datas; function __construct($datas = 'request') { $this->datas = $datas; } function beforeAction() { echo "<div style='color:{$this->datas};'>"; } function afterAction() { echo "</div>"; } } $Object = new \SomeClass(); $Object->addDecorator(new \OneDecorator('blue')); //Add other decorator... $Object->action();🎜그런 다음 다른 도구 기능을 사용하여 동일한 인터페이스를 구현하세요. 🎜🎜🎜🎜5: 전략 패턴 🎜🎜🎜🎜이점: 🎜🎜특정 특정 컨텍스트에 적응하고, 특정 구현에서 논리적 판단을 분리하고, 디커플링으로 하드 코딩을 구현하고 IOC를 활성화하기 위해 특정 동작 및 알고리즘 세트를 클래스로 캡슐화합니다. , 종속성 반전 및 반전 제어. 🎜🎜구현:🎜🎜1. 전략 인터페이스 파일(
UserStrategy.php
)을 정의하고, 전략 인터페이스를 정의하고, 전략을 선언합니다.🎜🎜2. 특정 클래스를 정의합니다. , MaleUserStrategy.php
), 전략 인터페이스를 구현하고 전략 메소드를 재정의합니다🎜Object::all() Iterator extends Traversable { //PHP内置迭代器接口 /* 方法 */ abstract public mixed current (void) abstract public scalar key (void) abstract public void next (void) abstract public void rewind (void) abstract public boolean valid (void) } class ObjectAll implements \Iterator { protected $ids; //所有对象的id protected $index; //迭代器的当前位置 protected $data = array(); //保存从数据库取到的所有对象 function __construct() { //取出所有的id,$ids } function current() { //获取当前的元素的数据,第三个调用 $id = $this->ids[$this->index]['id']; return Object::find($id); } function next() { //获取下一个元素,第四个调用 $this->index ++; } function valid() { //验证当前元素是否还有下一个元素(查询当前是否有数据),第二个调用 return $this->index < count($this->$ids); } function rewind() { //当迭代器执行到末尾时,重置迭代器到整个集合的开头,最先调用 $this->index = 0; } function key() { //获取当前的索引,最后调用 return $this->index; } } $objects = new \ObjectAll(); foreach ($objects as $row) { dump($row->field); //增删改查操作 }🎜🎜🎜6: 데이터 개체 매핑 모드🎜🎜🎜🎜이점: 개체 및 데이터 저장소 매핑, 매핑 객체 작업은 ORM의 구현 메커니즘이기도 한 데이터 저장소의 작업에 매핑됩니다. 🎜
interface DBproxy { function getInfo($id); function setInfo($id, $value); } class Proxy implements DBproxy { function get() { //DB::('slave'); query } function set() { //DB::('master'); query } } $proxy = new Proxy(); $proxy->get($id); $proxy->set($id, $value);🎜🎜🎜7: 관찰자 모드 🎜🎜🎜🎜사용: 🎜🎜Trigger 클래스
Event
🎜rrreee🎜Listening 클래스 EventListener
🎜rrreee🎜혜택: 🎜🎜언제가 되세요 객체의 상태가 변경되면 이에 의존하는 모든 객체는 알림을 받고 자동으로 업데이트되어 낮은 결합, 비침해 알림 및 업데이트 메커니즘을 달성합니다. 🎜🎜🎜🎜8: 프로토타입 모드 🎜🎜🎜🎜는 팩토리 모드와 유사하며 객체를 생성하는 데 사용됩니다. 차이점은 프로토타입 모드는 먼저 프로토타입 객체를 생성한 다음 프로토타입 객체를 복제하여 새로운 객체를 생성한다는 것입니다. 프로토타입 모드는 다음에 적합합니다. 대형 객체 생성에는 메모리 복사만 필요합니다. 🎜rrreee🎜🎜🎜9: 데코레이터 패턴 🎜🎜🎜🎜 클래스의 기능을 수정하거나 추가하기 위한 전통적인 방법은 하위 클래스를 작성하여 이를 상속하고 클래스 메서드를 다시 구현하는 것입니다. 데코레이터 패턴은 클래스의 기능을 동적으로 추가하거나 수정하기 위해 런타임에 데코레이터 객체를 추가하기만 하면 됩니다. 🎜🎜기존 방법:🎜class Method2 extends Method { function doSomething() { echo "<div style='color:red'>" parent::doSomething(); echo "</div>"; } } interfa Decorator { //定义装饰器接口 function beforeAction(); function afterAction(); //more decoratorMethod…… } class SomeClass { protected $decorators = []; function addDecorator(Decorator $decorator) { $this->decorators[] = $decorator; } function beforeMethod() { foreach ($this->decorators as $row) { $row->beforeAction(); } } function afterMethod() { $decorators = array_reverse($this->decorators); //做一个反转 foreach ($this->decorators as $row) { $row->afterAction(); } } function action() { $this->beforeMethod(); //method; $this->afterMethod(); } } class OneDecorator implements Decorator { protected $datas; function __construct($datas = 'request') { $this->datas = $datas; } function beforeAction() { echo "<div style='color:{$this->datas};'>"; } function afterAction() { echo "</div>"; } } $Object = new \SomeClass(); $Object->addDecorator(new \OneDecorator('blue')); //Add other decorator... $Object->action();
10:迭代器模式
在不需要了解内部实现的前提下,遍历一个聚合对象的内部元素,相对于传统编程方式它可以遍历元素所需的操作。
例如:
Object::all() Iterator extends Traversable { //PHP内置迭代器接口 /* 方法 */ abstract public mixed current (void) abstract public scalar key (void) abstract public void next (void) abstract public void rewind (void) abstract public boolean valid (void) } class ObjectAll implements \Iterator { protected $ids; //所有对象的id protected $index; //迭代器的当前位置 protected $data = array(); //保存从数据库取到的所有对象 function __construct() { //取出所有的id,$ids } function current() { //获取当前的元素的数据,第三个调用 $id = $this->ids[$this->index]['id']; return Object::find($id); } function next() { //获取下一个元素,第四个调用 $this->index ++; } function valid() { //验证当前元素是否还有下一个元素(查询当前是否有数据),第二个调用 return $this->index < count($this->$ids); } function rewind() { //当迭代器执行到末尾时,重置迭代器到整个集合的开头,最先调用 $this->index = 0; } function key() { //获取当前的索引,最后调用 return $this->index; } } $objects = new \ObjectAll(); foreach ($objects as $row) { dump($row->field); //增删改查操作 }
11:代理模式
在客户端与实体之间建立一个代理对象,客户端对实体进行操作全部委派给代理对象,隐藏实体的具体实现细节(slave
读库与master
写库分离)。代理对象还可以与业务代码分离,部署到另外的服务器,业务代码中通过PRC
来委派任务。
interface DBproxy { function getInfo($id); function setInfo($id, $value); } class Proxy implements DBproxy { function get() { //DB::('slave'); query } function set() { //DB::('master'); query } } $proxy = new Proxy(); $proxy->get($id); $proxy->set($id, $value);
相关推荐:最新的五个Laravel视频教程
위 내용은 laravel은 어떤 디자인 패턴을 사용합니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!