MVC原理与container, facade设计模式
一、MVC是一种架构模式,M-模型/V-视图/C-控制器
- 模型(Model):负责存储系统的中心数据。
- 视图(View):将信息显示给用户(可以定义多个视图)。
- 控制器(Controller):处理用户输入的信息。负责从视图读取数据,控制用户输入,并向模型发送数据,是应用程序中处理用户交互的部分。负责管理与用户交互交互控制。
1、MVC实例展示:
实例效果:
实例源码:
<?
//模型层:当前页面要显示的数据
$pdo = new PDO('mysql:host=localhost;dbname=study','root','123456');
$orders = $pdo->query('SELECT `id`,`name`,`pro`,`price` FROM `order` order by id asc LIMIT 8')->fetchAll(PDO::FETCH_ASSOC);
// print_r($orders);
?>
<!-- 视图层 -->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>订单数据显示</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<table width="100%" border="1" cellspacing="0" cellpadding="5">
<caption>用户信息表</caption>
<thead>
<tr>
<td>编号</td>
<td>姓名</td>
<td>项目</td>
<td>价格</td>
<td>操作</td>
</tr>
</thead>
<tbody>
<?php foreach($orders as $order):?>
<tr>
<td><?= $order['id']?></td>
<td><?= $order['name']?></td>
<td><?= $order['pro']?></td>
<td><?= $order['price']?></td>
<td><button>删除</button><button>编辑</button></td>
</tr>
<?php endforeach;?>
</tbody>
</table>
</body>
</html>
二、公共模型和视图类:
1、Model.php
<?php
namespace zhangfugen;
use PDO;
class Model {
//获取数据
public function getData()
{
return (new PDO('mysql:host=localhost;dbname=study','root','123456'))->query('SELECT `id`,`name`,`pro`,`price` FROM `order` order by id DESC LIMIT 10')->fetchAll(PDO::FETCH_ASSOC);
}
}
2、View.php
<?php
namespace zhangfugen;
//视图 : 数据展示
class View {
public function fetch($data){
$table = '<table>';
$table.= ' <caption>订单信息表</caption>';
$table.= '<tr><th>编号</th><th>名称</th><th>项目</th><th>价格</th></tr>';
foreach($data as $user){
$table.= '<tr>';
$table.=' <td>'.$user['id'].'</td>';
$table.=' <td>'.$user['name'].'</td>';
$table.=' <td>'.$user['pro'].'</td>';
$table.=' <td>'.$user['price'].'</td>';
$table.= '</tr>';
}
$table .= '</table>';
return $table;
}
}
echo '<style>
table {border-collapse: collapse; border: 1px solid;text-align: center; height: 480px;width: 780px;}
caption {font-size: 2rem; margin: 20px 0px;}
tr:first-of-type { background-color:lightgreen;}
td,th {border: 1px solid; padding:5px}
</style>';
三、参数注入在MVC原理应用:
<?php
// 参数注入在MVC原理应用:
namespace zhangfugen;
//加载模型 视图类
require 'Model.php';
require 'View.php';
class Controller{
public function index($model,$view)
{
//1. 获取数据
$data = $model->getData();
//2.模板渲染
return $view->fetch($data);
}
public function edit($model){
}
}
$contr = new Controller;
$model = new Model();
$view = new View();
echo $contr->index($model,$view);
四、实现外部对象在当前类中的共享(复用):
通过构造方法:
<?php
// 通过构造方法将实现外部对象在当前类中的共享(复用):
namespace zhangfugen;
//加载模型 视图类
require 'Model.php';
require 'View.php';
class Controller {
private $model;
private $view;
// 通过构造方法将外部对象初始化,实现了外部依赖注入的对象在类内部的共享/复用
public function __construct($model,$view){
$this->model = $model;
$this->view = $view;
}
public function index(){
//1. 获取数据
$data = $this->model->getData();
//2.模板渲染
return $this->view->fetch($data);
}
public function edit(){
}
public function uqdate(){
}
}
// 实例化类:
$model = new Model();
$view = new View();
// 外部对象的注入点放在了魔术方法
$contr = new Controller($model,$view);
echo $contr->index();
将外部对象放到一个”服务容器”中进行统一管理:
服务容器Container
<?php
// 将外部对象放到一个"服务容器"中进行统一管理
// 服务容器Container
namespace zhangfugen;
//引用基类Closure,是用于代表匿名函数的类
use Closure;
//加载模型 视图类
require 'Model.php';
require 'View.php';
// 服务容器: 一个自动产生类/对像的工厂
class Container {
//1. 定义对象容器:
protected $instances = [];
// 2. 对象容器中添加对象
// $abstract 类标识,当前容器数组中的键名/别名
// $concrete 要绑定的类, 闭包或者实例,实现方法
public function bind($abstract, Closure $concrete)
{
$this->instances[$abstract] = $concrete;
}
// 3.从对象容器中取出对象, 调用
public function make($abstract,$params=[])
{
return call_user_func_array($this->instances[$abstract],$params);
}
}
$container = new Container;
// 将外部对象: Model, View的实例绑定到服务容器中
$container->bind('model',function(){
return new Model();
});
$container->bind('view',function(){
return new View();
});
class Controller {
// 控制器获取数据,并展示出来
public function index(Container $container){
//1. 获取数据
$data = $container->make('model')->getData();
//2.模板渲染
return $container->make('view')->fetch($data);
}
}
// 实例化输出
$contr = new Controller();
echo $contr->index($container);
Facade门面技术静态接管服务容器中对象的访问:
<?php
// Facade门面技术静态接管服务容器中对象的访问
namespace zhangfugen;
//引用基类Closure,是用于代表匿名函数的类
use Closure;
//加载模型 视图类
require 'Model.php';
require 'View.php';
// <=========================================================================>
// 服务容器: 一个自动产生类/对像的工厂
// 将外部对象放到一个"服务容器"中进行统一管理
class Container {
//1. 定义对象容器:
protected $instances = [];
// 2. 对象容器中添加对象
// $abstract 类标识,当前容器数组中的键名/别名
// $concrete 要绑定的类, 闭包或者实例,实现方法
public function bind($abstract, Closure $concrete)
{
$this->instances[$abstract] = $concrete;
}
// 3.从对象容器中取出对象, 调用
public function make($abstract,$params=[])
{
return call_user_func_array($this->instances[$abstract],$params);
}
}
$container = new Container;
// 将外部对象: Model, View的实例绑定到服务容器中
$container->bind('model',function(){
return new Model();
});
$container->bind('view',function(){
return new View();
});
// <==========================================================================>
// Facade门面技术静态接管服务容器中对象的访问
// 服务容器与工作的控制器之间再添加一个中间层: Facade
class Facade {
protected static $container = null;
// 给当前facade类中的$container属性进行赋值,将container注入到当前facade类中
public static function initialize(Container $container )
{
static::$container = $container;
}
}
//模型类 成员的访问静态化:
class UserModel extends Facade
{
public static function getData()
{
//后期静态绑定
return static::$container->make('model')->getData();
}
}
//视图类 成员的访问静态化:
class UserView extends Facade
{
public static function fetch($data)
{
//后期静态绑定
return static::$container->make('view')->fetch($data);
}
}
// <==========================================================================>
class Controller {
//构造方法,初始化facade
public function __construct(Container $container)
{
Facade::initialize($container);
}
//使用门面技术facade方式 访问成员
public function index()
{
//1. 获取数据
$data = UserModel::getData();
//2.模板渲染
return UserView::fetch($data);
}
}
// 实例化输出
$contr = new Controller($container);
echo $contr->index();