PHP中常用的三种设计模式详解【单例模式、工厂(2)

<?php
/**
 * php单例,单例模式为何只能实例化一次
*/
class Example{
  // 保存类实例在此属性中
  private static $instance;
  // 构造方法声明为private,防止直接创建对象
  private function __construct(){
    echo 'I am constructed';
  }
  // singleton 方法
  public static function singleton(){
    if (!isset(self::$instance)) {//判断是否以前创建了当前类的实例
      $c = __CLASS__;//获取类名
      self::$instance = new $c;//如果没有创建,实例化当前类,这里实现类只实例化一次
    }
    return self::$instance;//返回类的实例
  }
  // Example类中的普通方法
  public function bark(){
    echo 'Woof!';
  }
  // 阻止用户复制对象实例
  public function __clone(){
    trigger_error('Clone is not allowed.', E_USER_ERROR);
  }
}
// 这个写法会出错,因为构造方法被声明为private
$test = new Example;
// 下面将得到Example类的单例对象
$test = Example::singleton();
$test->bark();
// 下面将得到Example类的单例对象
$test = Example::singleton();
$test->bark();
// 复制对象将导致一个E_USER_ERROR.
$test_clone = clone $test;
?>

关于__clone()方法可参考: PHP对象克隆__clone()介绍

2. 工厂模式

工厂模式在于可以根据输入参数或者应用程序配置的不同来创建一种专门用来实现化并返回其它类的实例的类。

工厂模式的例子:

<?php
class FactoryBasic {
  public static function create($config) {
  }
}

比如这里是一个描述形状对象的工厂,它希望根据传入的参数个数不同来创建不同的形状。

<?php
// 定义形状的公共功能:获取周长和面积。
interface IShape {
  function getCircum();
  function getArea();
}
// 定义矩形类
class Rectangle implements IShape {
  private $width, $height;
  public function __construct($width, $height) {
    $this->width = $width;
    $this->height = $height;
  }
  public function getCircum() {
    return 2 * ($this->width + $this->height);
  }
  public function getArea() {
    return $this->width * $this->height;
  }
}
// 定义圆类
class Circle implements IShape {
  private $radii;
  public function __construct($radii) {
    $this->radii = $radii;
  }
  public function getCircum() {
    return 2 * M_PI * $this->radii;
  }
  public function getArea() {
    return M_PI * pow($this->radii, 2);
  }
}
// 根据传入的参数个数不同来创建不同的形状。
class FactoryShape {
  public static function create() {
    switch (func_num_args()) {
      case 1:
      return new Circle(func_get_arg(0));
      break;
      case 2:
      return new Rectangle(func_get_arg(0), func_get_arg(1));
      break;
    }
  }
}
// 矩形对象
$c = FactoryShape::create(4, 2);
var_dump($c->getArea());
// 圆对象
$o = FactoryShape::create(2);
var_dump($o->getArea());


      

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:http://www.heiqu.com/5538.html