PHP OPP机制和模式简介(抽象类、接口和契约式编程)


Posted in PHP onJune 09, 2014

1.抽象类

抽象类机制中总是要定义一个公共的基类,而将特定的细节留给继承者来实现。通过抽象概念,可以在开发项目中创建扩展性很好的架构。任何一个类,如果它里面至少有一个方法是被声明为抽象的,那么这个类就必须被声明为抽象的。被定义为抽象的方法只是声明了其调用方式(参数),不能定义其具体的功能实现。在类的声明中使用 abstract 修饰符就可以将某个类声明为抽象的。

1.1方法原型(prototype)

是指方法的定义中剔除了方法体之后的签名。它包括存取级别、函数关键字、函数名称和参数。他不包含({})或者括号内部的任何代码。例如下面的代码就是一个方法原型:

public function prototypeName($protoParam)

继承一个抽象类的时候,子类必须定义父类中的所有抽象方法;另外,这些方法的访问控制必须和父类中一样(或者更为宽松)。

1.2关于抽象类

    某个类只要包含至少一个抽象方法就必须声明为抽象类
    声明为抽象的方法,在实现的时候必须包含相同的或者更低的访问级别。
    不能使用 new 关键字创建抽象类的实例。
    被生命为抽象的方法不能包含函数体。
    如果将扩展的类也声明为抽象类,在扩展抽象类时,可以不用实现所有的抽象方法。(如果某个类从抽象类继承,当它没有实现基类中所声明的所有抽象方法时,它就必须也被声明为抽象的。)

1.3使用抽象类

<?php
abstract class Car
{    
    abstract function getMaxSpeend();
}
class Roadster extends Car
{
    public $Speend;
    public function SetSpeend($speend = 0)
    {
        $this->Speend = $speend;
    }
    public function getMaxSpeend()
    {
        return $this->Speend;
    }
}
class Street
{
    public $Cars ;
    public $SpeendLimit ;
    function __construct( $speendLimit = 200)
    {
        $this -> SpeendLimit = $speendLimit;
        $this -> Cars = array();
    }
    protected function IsStreetLegal($car)
    {
        if ($car->getMaxSpeend() < $this -> SpeendLimit)
        {
            return true;
        }
        else
        {
            return false;
        }
    }
    public function AddCar($car)
    {
        if($this->IsStreetLegal($car))
        {
            echo 'The Car was allowed on the road.';
            $this->Cars[] = $car;
        }
        else
        {
            echo 'The Car is too fast and was not allowed on the road.';
        }
    }
}
$Porsche911 = new Roadster();
$Porsche911->SetSpeend(340);
$FuWaiStreet = new Street(80);
$FuWaiStreet->AddCar($Porsche911);
/**
 *
 * @result
 * 
 * The Car is too fast and was not allowed on the road.[Finished in 0.1s]
 *
 */
?>

2.对象接口

使用接口(interface),可以指定某个类必须实现哪些方法,但不需要定义这些方法的具体内容。

接口是通过 interface 关键字来定义的,就像定义一个标准的类一样,但其中定义所有的方法都是空的。

接口中定义的所有方法都必须是公有,这是接口的特性。

接口是一种类似于类的结构,可用于声明实现类所必须声明的方法。例如,接口通常用来声明API,而不用定义如何实现这个API。

    大多数开发人员选择在接口名称前加上大写字母I作为前缀,以便在代码和生成的文档中将其与类区别开来。

2.1使用接口

和集成抽象类需要使用 extends 关键字不同的是,实现接口使用的是 implements 关键字。一个类可以实现多个接口,这时,我们需要用逗号将他们隔开。如果将某个类标记为实现了某个接口,但却没有实现这个借口的所有方法,将会抛出错误。

2.2使用接口的案例

<?php
abstract class Car
{    
    abstract function SetSpeend($speend = 0);
}
interface ISpeendInfo
{
    function GetMaxSpeend();
}
class Roadster extends Car implements ISpeendInfo
{
    public $Speend;
    public function SetSpeend($speend = 0)
    {
        $this->Speend = $speend;
    }
    public function getMaxSpeend()
    {
        return $this->Speend;
    }
}
class Street
{
    public $Cars ;
    public $SpeendLimit ;
    function __construct( $speendLimit = 200)
    {
        $this -> SpeendLimit = $speendLimit;
        $this -> Cars = array();
    }
    protected function IsStreetLegal($car)
    {
        if ($car->getMaxSpeend() < $this -> SpeendLimit)
        {
            return true;
        }
        else
        {
            return false;
        }
    }
    public function AddCar($car)
    {
        if($this->IsStreetLegal($car))
        {
            echo 'The Car was allowed on the road.';
            $this->Cars[] = $car;
        }
        else
        {
            echo 'The Car is too fast and was not allowed on the road.';
        }
    }
}

$Porsche911 = new Roadster();
$Porsche911->SetSpeend(340);
$FuWaiStreet = new Street(80);
$FuWaiStreet->AddCar($Porsche911);
/**
 *
 * @result
 * 
 * The Car is too fast and was not allowed on the road.[Finished in 0.1s]
 *
 */
?>

3.instanceof 操作符

instanceof 操作符是PHP5中的一个比较操作符。他接受左右两边的参数,并返回一个boolean值。这个操作符是用来确定对象的某个实例是否为特定的类型,或者是否从某个类型继承,又或者实现类某个特定的接口。

echo $Porsche911 instanceof Car;
//result:1
echo $Porsche911 instanceof ISpeendInfo;
//result:1

4.契约式编程

契约式编程是指在编写类之前实现声明接口的一种编程实践。这种方法在保证类的封装性方面非常有用。使用契约式编程技术,我们可以在创建应用程序之前定义出视图实现的功能,这和建筑师在修建大楼之前先画好蓝图的做法非常相似。

5.总结

抽象类是使用 abstract 关键字声明的类。通过将某个类标记为抽象类,我们可以推迟实现所声明的方法。要将某个方法声明为抽象方法,只要去掉包含所有大括号的方法实体,将方法声明的代码行用分号结束即可。

抽象类不能直接实例化,他们必须被继承。

如果某个类从抽象类继承,当它没有实现基类中所声明的所有抽象方法时,它就必须也被声明为抽象的。

在接口中,我们可以声明没有方法体的方法原型,这点与抽象类很相似。他们之间的区别在于,接口不能声明任何具有方法体的方法;并且他们使用的语法也不一样。为了将揭开规则强制加到某个类上,我们需要使用implements关键字,而不是extends关键字。

有些情况下我们需要确定某个类是否是特定类的类型,或者是否实现了特定的接口。 instanceof 分成适合完成这个任务。instanceof 检查三件事情:实例是否是某个特定的类型,实例是否从某个特定的类型继承,实例或者他的任何祖先类是否实现类特定的接口。

某些语言具有从多个类继承的能力,这称为多重继承。PHP不支持多重继承。想法,他提供了为一个类声明多个接口的功能。

接口在声明类必须遵循的规则时非常有用。契约式编程技术使用这一功能来增强封装性,优化工作流。

PHP 相关文章推荐
基于mysql的论坛(6)
Oct 09 PHP
PHP 5.0对象模型深度探索之类的静态成员
Mar 27 PHP
PHP中simplexml_load_string函数使用说明
Jan 01 PHP
PHP内核介绍及扩展开发指南―基础知识
Sep 11 PHP
PHP字符串中特殊符号的过滤方法介绍
Feb 18 PHP
thinkphp实现面包屑导航(当前位置)例子分享
May 10 PHP
php实现编辑和保存文件的方法
Jul 20 PHP
PHP基于mssql扩展远程连接MSSQL的简单实现方法
Oct 08 PHP
利用PHPExcel读取Excel的数据和导出数据到Excel
May 12 PHP
PHP读取word文档的方法分析【基于COM组件】
Aug 01 PHP
PHP定义字符串的四种方式详解
Feb 06 PHP
php PDO属性设置与操作方法分析
Dec 27 PHP
PHP+ajaxfileupload+jcrop插件完美实现头像上传剪裁
Jun 09 #PHP
神盾加密解密教程(三)PHP 神盾解密工具
Jun 08 #PHP
神盾加密解密教程(二)PHP 神盾解密
Jun 08 #PHP
IIS6.0 开启Gzip方法及PHP Gzip函数分享
Jun 08 #PHP
PHP获取中英混合字符串长度的方法
Jun 07 #PHP
使用PHP破解防盗链图片的一个简单方法
Jun 07 #PHP
PHP防止post重复提交数据的简单例子
Jun 07 #PHP
You might like
php中怎么搜索相关联数组键值及获取之
2013/10/17 PHP
Linux下PHP安装mcrypt扩展模块笔记
2014/09/10 PHP
总结PHP如何获取当前主机、域名、网址、路径、端口和参数等
2016/09/09 PHP
PHPUnit测试私有属性和方法功能示例
2018/06/12 PHP
javaScript 删除字符串空格多种方法小结
2012/10/24 Javascript
Node.js中child_process实现多进程
2015/02/03 Javascript
JavaScript中setUTCFullYear()方法的使用简介
2015/06/12 Javascript
JavaScript操作URL的相关内容集锦
2015/10/29 Javascript
实例讲解JavaScript中instanceof运算符的用法
2016/06/08 Javascript
js仿手机页面文件下拉刷新效果
2016/10/14 Javascript
详解webpack require.ensure与require AMD的区别
2017/12/13 Javascript
利用d3.js力导布局绘制资源拓扑图实例教程
2019/01/08 Javascript
JavaScript使用Math.random()生成简单的验证码
2019/01/21 Javascript
vue实现的仿淘宝购物车功能详解
2019/01/27 Javascript
JQuery常见节点操作实例分析
2019/05/15 jQuery
微信小程序多列表渲染数据开关互不影响的实现
2020/06/05 Javascript
浅析JavaScript 函数防抖和节流
2020/07/13 Javascript
[02:47]3.19DOTA2发布会 国服成长历程回顾
2014/03/25 DOTA
Python中的异常处理相关语句基础学习笔记
2016/07/11 Python
python2.7+selenium2实现淘宝滑块自动认证功能
2018/02/24 Python
Python实现二维曲线拟合的方法
2018/12/29 Python
python 字典操作提取key,value的方法
2019/06/26 Python
使用Python做垃圾分类的原理及实例代码附源码
2019/07/02 Python
python3.x+pyqt5实现主窗口状态栏里(嵌入)显示进度条功能
2019/07/04 Python
python 爬取疫情数据的源码
2020/02/09 Python
使用PyQt的QLabel组件实现选定目标框功能的方法示例
2020/05/19 Python
css3实现波纹特效、H5实现动态波浪效果
2018/01/31 HTML / CSS
DataReader和DataSet的异同
2014/12/31 面试题
财务管理专业应届毕业生求职信
2013/09/22 职场文书
大学毕业生的自我鉴定
2013/11/30 职场文书
物流管理专业职业生涯规划书
2014/01/06 职场文书
党员干部承诺书
2014/03/25 职场文书
幼儿园课题方案
2014/06/09 职场文书
会计个人实习计划书
2014/08/15 职场文书
先进教师个人主要事迹材料
2015/11/03 职场文书
2016年离婚协议书范文
2016/03/18 职场文书