首先,设计模式出如今眼里太屡次了,看了又看,忘了又忘,咋看咋忘,在作前端开发之时就看过相关型文章,水平有限,业务有限,看过的知识比如过往云烟,匆匆而已,不留下一点痕迹,现在做为一个php,我决定深深的探一下设计模式,对于项目的开发以及代码的规范有着大大的好处。php
一、单例是设计模式里最基础的一种
二、我用过单例
三、我不是什么大神,只是一个初转后端的小白。前端
一、建立型设计模式的一种。
二、字面意思(单个例子,单个实例)。
复制代码
一、在特定的场景里,特定的类只能有一个实例。
二、节约内存。
复制代码
一、自行实例化。
二、只有一个实例。
三、向全局暴露实例。
复制代码
首先先模拟一个故事。数据库
小时候最头疼写做业,语文做业,英语做业等等,很是多,而后写做的时候须要用到笔,通常我是直接用一个笔写完做业,不多是写语文做业用一支笔,写英语做业用另外一只笔。而后以这个故事用代码来描述一下。后端
代码部分设计模式
一、先抽象一个笔类函数
class Pen {
public function __construct(){
echo "制做一支笔";
}
public function write() {
echo "我能够写字";
}
}
复制代码
这个类叫作pen,有一个方法叫写,通俗的讲,抽象一个笔,这个笔有一个功能叫作写字。测试
二、 而后使用它spa
class Xiaochen {
public function writeEnglish(): Pen {
$pen = new Pen();
$pen->write();
echo "写英语<br>";
return $pen;
}
public function writeChinese(): Pen {
$pen = new Pen();
$pen->write();
echo "写英语<br>";
return $pen;
}
}
复制代码
抽象一我的,叫小陈,小陈今天要写语文和数学做业(writeEnglish,writeChinese),而后小陈写做业的时候确定要用到笔($pen=new Pen)。这样就能够完成了使用。 结果是这样: 设计
三、而后咱们来判断一下写语文和写做业是否是用的一支笔日志
var_dump($writeChinesePen === $writeChinesePen);
答案是false。
复制代码
由于虽然是统一的pen类实例出来的对象,可是两个对象倒是不一样的存在,至于为何,不懂的能够去补一下基础。
四、修改pen类
class Pen {
// 定义静态,全局可访问的实例对象
private static $pen;
// 暴露一个实例化的方法,只能经过这个方法实例化
public static function getInstance() {
if(is_null(static::$pen)) {
static::$pen = new static;
}
return static::$pen;
}
public function write() {
echo "写字";
}
}
复制代码
一、首先预约义一个全局的属性用来存储实例对象,使用static,由于没必要实例化就可使用。
二、制做一个方法,代替实例化,判断,若是实例过,直接返回实例对象,else,进行实例化。
三、若是有人不知道,使用new操做符来实例这个类怎么办。(不懂的请观看访问控制相关的文档)
答案是修改构造函数:
private function __construct(){
}
复制代码
四、因为类是继承,那么单例也就表明着单例类不可继承,而且不可复制。
修改php内置的clone:
private function __clone() {
}
复制代码
修改类不可继承 final class Pen
这样的话,这个笔类大体就完成了。不可经过new操做符进行实例,也不会建立多个实例。由于是static,因此全局均可以使用。
五、最终测试
final class Pen {
// 定义静态,全局可访问的实例对象
private static $pen;
// 暴露一个实例化的方法,只能经过这个方法实例化
public static function getInstance() {
if(is_null(static::$pen)) {
static::$pen = new static;
}
return static::$pen;
}
public function write() {
echo "写字";
}
private function __construct(){
}
private function __clone() {
}
}
class Xiaochen {
public function writeEnglish(): Pen {
$pen = Pen::getInstance();
$pen->write();
echo "写英语<br>";
return $pen;
}
public function writeChinese(): Pen {
$pen = Pen::getInstance();
$pen->write();
echo "写数学<br>";
return $pen;
}
}
$xiaochen = new Xiaochen();
$writeEnglistPen = $xiaochen->writeEnglish();
$writeChinesePen = $xiaochen->writeChinese();
var_dump($writeChinesePen === $writeEnglistPen);
复制代码
这样就能够保证全局只有一个实例,不会建立多个实例,只要实例过一次,就不会在建立第二个实例。
以单例开始设计模式之门,以上例子纯属我的编造,可能有写不恰当,大神勿喷,单例在应用种我通常都用来初始化数据库链接,日志对象,以及须要设定全局只有一个实例的需求。