抽象类,接口
Posted Just do it
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了抽象类,接口相关的知识,希望对你有一定的参考价值。
抽象类
定义一个公共的基类(base class),而将特定的细节留给继承者来实现.
由于抽象类没有为它所声明的所有方法都定义实现,所以使用new操作符是不可以直接创建它的实例的.要创建实例,就必须创建另一个扩展抽象类的类,并重写所有之前声明的抽象方法原型.通过扩展类,我们就可以创建特殊的对象,而且它们同样能够保证提供一套公共的功能.
说明:方法的原型(prototype)是指方法的定义中剔除了方法体之后的签名.它包括存取级别,函数关键字,函数名和参数,它不包括({})或者括号内部的任何代码.例如 public function prototypeName($protoparam);就是一个i额方法的原型.
抽象类的特点:
1.某个类只要包含至少一个抽象方法就必须声明为抽象类.
2.声明为抽象的方法,在实现的时候必须包含相同的或者更低的访问级别.例如,如果某个方法在抽象类中的访问级别是受保护的,在继承类中就必须是受保护的或者公共的,而不能是私有的.
3.不能使用new关键字创建抽象类的实例.
4.被声明为抽象的方法不能包含函数体.
5.如果将扩展的类也声明为抽象的,在扩展抽象类时,就可以不能实现所有的抽象方法.在创建具有层次结构的对象时,这种做法是很有用的.
在类的声明中使用abstract修饰符就可以将某个类声明为抽象的.
<?php abstract class Car{ //任何基类方法 abstract function getMaximumSpeed(); } class FastCar extends Car{ function getMaximumSpeed(){ return 150; } } class Street{ protected $speedLimit; protected $cars; public function __construct($speedLimit = 200){ $this->cars = array(); //对变量进行初始化 $this->speedLimit = $speedLimit; } protected function isStreetLegal($car){ if($car->getMaximumSpeed() < $this->speedLimit){ return true; }else{ return false; } } public function addCar($car){ if($this->isStreetLegal($car)){ echo \'The Car was allowed on the road.\'; $this->car[] =$car; }else{ echo \'The Car is too fast and was not allowed on the road.\'; } } } $street = new Street(); $street->addCar(new FastCar());
使用抽象类,我们就可以确定所有继承自Car的对象都会实现getMaximumSpeed()方法,从而
共享这个公共的功能.如果继承自Car的类没有定义这个方法,就会导致语法错误,程序也不会允许.
然而,抽象类也有一些限制.php只支持从一个基类继承,而不支持从两个或者更多的抽象类继承.用接口可以达到相同的目的.
接口
接口是一种类似于类的结构,可用于声明实现类所必须声明的方法.例如,接口通常用来声明API,而不用定义如何实现这个API.
虽然接口与抽象类很相似,但是接口只能包含方法原型,而不能包含任何完整定义了的方法.这可以防止使用抽象类时可能出现的方法冲突,从而能在给定的实现类上使用多个接口.
声明接口,需要使用关键字interface.
interface IExampleInterface{}
和抽象类需要使用extends关键字不同的是,实现接口使用的是implements关键字.
Class ExampleClass implements IExampleInterface{}
为了形成一个完整的类,我们必须实现接口中的所有方法,这样其他类才能依赖于接口中定义的所有方法.只要有一个接口方法没有实现,就会破坏定义公共接口的作用,因而这是不允许的.
//实现多接口 Class MyArrayLikeObject implements Iterator,Countable {}
抽象类和接口使用原则
使用接口完全有可能实现与抽象类相同的操作.通常,在子类和父类之间存在有逻辑上的层次结构时,应该使用抽象类.而在希望支持差别较大的两个或者更多对象之间的特定交互行为时,使用抽象类就会显得不合理,此时应该使用接口.
instanceof 操作符
instanceof操作符是PHP中的一个比较操作符.接受左右两边的参数,并返回Boolean类型的值.这个操作符是用来确定对象的某个实例是否为特定的类型,或者是否从某个类型继承,又或者是否实现了某个特定的接口.
上例代码用接口实现:
interface ISpeedInfo{ function getMaximumSpeed(); } class Car{ //任何基类方法 } class FastCar extends Car implements ISpeedInfo{ function getMaximumSpeed(){ return 150; } } class Street{ protected $speedLimit; protected $cars; public function __construct($speedLimit = 200){ $this->cars = array(); //对变量进行初始化 $this->speedLimit = $speedLimit; } protected function isStreetLegal($car){ if($car instanceof ISpeedInfo){ if($car->getMaximumSpeed() < $this->speedLimit){ return true; }else{ return false; } }else{ //扩展类必须实现ISpeedInfo才能使street合法 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.\'; } } } $street = new Street(); $street->addCar(new Street());
以上是关于抽象类,接口的主要内容,如果未能解决你的问题,请参考以下文章
Kotlin接口和抽象类 ( 接口属性和方法定义 | 接口默认方法实现 | 抽象类 )