Correcting teacher:天蓬老师
Correction status:qualified
Teacher's comments:有时不得不佩服发明这些设计模式的人, 折磨了一代又一代的程序员, 同学你的头发还好吧
一、将课堂代码全部上机操作至少一遍以上,代码中的注释文字, 不得少于代码量的四分之一
1、单例模式
<?php namespace _1205; class Work { } $obj1 = new Work(); $obj2 = new Work(); var_dump($obj1,$obj2); echo '<br>'; var_dump($obj1 === $obj2); echo '<hr>'; class Work1 { //使用private使构造方法私有化,从而不能从外部new private function __construct() { } //只能在当前类里面实例化 public static $instance; //实例化当前类的方法 public static function getInstance() { //判断当前类是否被实例化,没有就实例化,有就返回 if(is_null(static::$instance)){ static::$instance = new self(); } return static::$instance; } // 禁用克隆魔术方法 private function __clone() { // ... } } $obj1 = Work1::getInstance(); $obj2 = Work1::getInstance(); var_dump($obj1,$obj2); echo '<br>'; var_dump($obj1 === $obj2); echo '<hr>'; //应用:连接数据库 class Db1 { //私有化构造方法,并传递连接参数 private function __construct(...$conn) { $dsn = $conn[0]; $username = $conn[1]; $password = $conn[2]; static::$pdo = new \PDO($dsn,$username,$password); } //只能在当前类里面实例化 public static $pdo; //实例化当前类的方法 public static function getInstance(...$conn) { //判断当前类是否被实例化,没有就实例化,有就返回 if(is_null(static::$pdo)){ new self(...$conn); } return static::$pdo; } // 禁用克隆魔术方法 private function __clone() { // ... } } $conn = ['mysql:host=localhost;dbname=movie', 'root', 'root']; $pdo = Db1::getInstance(...$conn); echo '<pre>' . print_r($pdo->query('select * from `users`')->fetchAll(\PDO::FETCH_ASSOC),true) . '</pre>';
点击 "运行实例" 按钮查看在线实例
2、工厂模式
<?php namespace _1205; class Work1 { public function __construct($arg1) { echo '对象创建成功,参数是:' . $arg1; } } class Work2 { public function __construct($arg1,$arg2) { echo '对象创建成功,参数是:' . implode(',',[$arg1,$arg2]); } } class Work3 { public function __construct($arg1,$arg2,$arg3) { echo '对象创建成功,参数是:' . implode(',',[$arg1,$arg2,$arg3]); } } //工厂模式,专用于创建实例 class Factory { //传入两个参数,一个是要创建的类名字,以及其他参数 public static function create($className,...$argments) { return new $className(...$argments); } } //用工厂模式创建对象 Factory::create(Work1::class,100); echo '<br>'; Factory::create(Work2::class, 100, 200); echo '<br>'; Factory::create(Work3::class, 100, 200, 300);
点击 "运行实例" 按钮查看在线实例
3、容器
<?php // 容器类 namespace _1205; // 引用闭包别名 use Closure; class Container { // 类实例容器 protected $instance = []; // 将类实例化的过程绑定到容器中 public function bind($alias, Closure $process) { $this->instance[$alias] = $process; } // 取出保存在容器中的实例化过程的闭包,并执行它 public function make($alias) { return $this->instance[$alias](); } }
点击 "运行实例" 按钮查看在线实例
<?php namespace _1205; // 制造商 class Maker { public function get() { return '华为'; } }
点击 "运行实例" 按钮查看在线实例
<?php namespace _1205; // 商品类 class Product { public function get(Maker $maker) { return '该手机是由: <span style="color:red;font-weight: bolder">' . $maker->get() . ' </span>生产的'; } }
点击 "运行实例" 按钮查看在线实例
<?php namespace _1205; require 'Product.php'; require 'Maker.php'; require 'Container.php'; //使用容器 class Work2 { //输出商品和制造商 public function show(Product $product,Maker $maker) { //制造商注入到产品类 return $product->get($maker); } } //实例化容器 $container = new Container(); //将实例化过程绑定到容器中 $container->bind('product',function (){return new Product();}); $container->bind('maker',function (){return new Maker();}); //从容器中拿出实例 $product = $container->make('product'); $maker = $container->make('maker'); echo (new Work2())->show($product,$maker);
点击 "运行实例" 按钮查看在线实例
4、接口
<?php namespace base\inc2; // 交通工具的接口 interface iVehicle { public function drive(); }
点击 "运行实例" 按钮查看在线实例
<?php namespace base\inc2; class Car implements iVehicle { public function drive() { return '开汽车'; } }
点击 "运行实例" 按钮查看在线实例
<?php // 旅行类: 使用接口方式 namespace base; // 设置引用的外部类名的别名 use base\inc2\Car; use base\inc2\Train; use base\inc2\Plane; use base\inc2\Ship; use base\inc2\iVehicle; require __DIR__ . '/autoload.php'; class Travel3 { // 交通工具 private $vehicle; // 构造方法 public function __construct(iVehicle $vehicle) { $this->vehicle = $vehicle; } // 调用外部一个依赖对象 public function travelModel() { return $this->vehicle->drive() . ' : ~~~~~ 去旅行'; } } // 客户端调用,传入的是对象 $car = new Car(); echo (new Travel3($car))->travelModel(), '<br>'; echo (new Travel3(new Train()))->travelModel(), '<br>'; echo (new Travel3(new Plane()))->travelModel(), '<br>'; echo (new Travel3(new Ship()))->travelModel(), '<br>';
点击 "运行实例" 按钮查看在线实例
二、手写课堂笔记:1205.md
三、总结
1、面向接口,注意传入的参数是实例对象
2、工厂模式,静态调用