PHP类之Trait实现代码复用效果图:
PHP类之Trait实现代码复用源代码:
实例
<?php //声明父类:Program if (!class_exists('Program')) { class Program { protected $name; public function __construct($name='小威') { $this->name = $name; } public function look($movie='功夫之王') { return $this->name.'喜欢观看'.'【'.$movie.'】'; } } } //声明trait类:Movie 电影 if(!trait_exists('Movie')){ trait Movie { //trait中也可以创新自己的属性 public $friend='小丽'; public function listen($music='中国人') { //trait中可以直接访问父类中的属性 继承关系 return $this->name.'和'.$this->friend.'在听'.'{'.$music.'}'; } //在trait中也声明一个与父类同名的study()方法,参数修改一下以示区别 public function look($movie='功夫') { return $this->friend.'喜欢观看'.'【'.$movie.'】'; } } } //声明trait类:Recreation 娱乐 if(!trait_exists('Recreation')){ trait Recreation { public $friend1='小军'; public function listen($music='中国心') { //trait中可以访问父类中的属性 return $this->name.'和'.$this->friend1.'在听'.'{'.$music.'}'; } } } //声明子类:Audience 继承自 父类:Program class Audience extends Program { //导入trait类,用以下语句解决trait中重名问题 use Movie, Recreation { //访问music()方法冲突时,使用Movie::music()代替掉Recoreation::muisc() Movie::listen insteadof Recreation; //再访问Recoreation::music()时启用别名 myMusic() Recreation::listen as mylisten; } //子类中必须实现trait中声明的抽象方法hobby() public static function hoddy($name) { return $name; } //在子类中再声明一个与trait类同名的study()方法,参数修改一下以示区别 public function look($movie='美人鱼') { return $this->name.'在观看'.'【'.$movie.'】'; } } //实例化Audience类 $audience = new Audience(); //1.访问父类Program类 echo $audience->look(); echo '<hr>'; //2.访问trait类中的方法 echo $audience->listen().'<br>'; echo $audience->look(); echo '<hr>'; //3.调用trait中的抽象静态方法,必须要用Audience来访问 echo Audience::hoddy('在电影院:喝可乐,吃爆米花').'<br>'; echo $audience->look().','.'同时'.Audience::hoddy('喝可乐,吃爆米花'); echo '<hr>'; //4.当trait中存在与父类同名方法时,trait优先级要高 echo $audience->mylisten(); echo '<hr>'; //5.当子类中存在与trait类同名方法时,子类优先级要高 echo $audience->look(); echo '<hr>'; //6.子类可以从多个trait中获取方法集 echo $audience->listen(); echo '<hr>'; echo $audience->mylisten();
运行实例 »
点击 "运行实例" 按钮查看在线实例
知识点:
Trait
* 1.trait是为单继承语言量身定制的代码复用机制;
* 2.之前可以通过函数或类来实现代码复用;
* 3.trait可以简单的理解为一个类方法的集合,工作在父类与子类之间;
* 4.但是trait不仅仅局限于方法集合,还支持抽象,静态与属性;
* 5.当前类成员会覆盖trait类成员,而trait中的成员,又可以覆盖同名类成员
* 6.重要提示:trait不是类,不能实例化,切记切记
trait中同样支持抽象,以及静态方法,我放在一起写了
//我把这个方法声明为抽象的同时,也声明为静态
abstract public static function hobby($name);
调用trait中的抽象静态方法,必须要用Audience来访问
当trait中存在与父类同名方法时,trait优先级要高
当子类中存在与trait类同名方法时,子类优先级要高
接口
* 1.使用关键字:interface
* 2.类是对象的模板,接口是类的模板
* 3.接口看作是一个特殊的类
* 4.接口中的方法,只声明不实现,与抽象类一样
* 5.接口中的方法必须是public,支持static
* 6.接口中可以声明类常量const,但不允许被类或子接口覆盖
* 7.用类实现一个接口使用implements 关键字
* 8.一个类可以实现多个接口,多个接口之间用逗号分开
* 9.接口之间也可以使用关键字extends继承
* 10.一个类实多个接口时,方法不可以重名
实例
<? php //声明接口:动物 if (!interface_exists('Animal')) { interface Animal { //接口常量 const status = 'viable'; //能存活的 //接口方法:饲养时吃什么 public function feeding($foods); } } //声明类Cat,并实现接口Animal if (interface_exists('Animal')) { class Cat implements Animal { private $name = '猫'; //在类中必须实现接口中的方法feeding() public function feeding($foods) { return $this->name.'吃'.$foods; } } } //实例化Dog类, echo (new Cat())->feeding('老鼠'); echo '<hr>'; //再定义一个接口:动物的特性 if (!interface_exists('Feature')) { interface Feature { //接口方法 public function hobby($hobby); } } //声明一个类Dog,实现了二个接口: Animal,Feature if (interface_exists('Animal') && interface_exists('Feature')) { class Dog implements Animal, Feature { private $name = '狗'; //必须实现接口Animal中的feeding()方法 public function feeding($foods) { // return $this->name.'吃'.$foods; //改成链式 echo $this->name.'吃'.$foods; return $this; } //必须实现接口Feature中的hobby()方法 public function hobby($hobby) { // return $hobby; //改成链式 echo $hobby; return $this; } } } //实例化Dog类 echo (new Dog())->feeding('肉'); echo (new Dog())->hobby('忠诚,勇敢,不离不弃~~'); //大家想想如何将上面的二个方法调用改成链式? //注意:先把上面的实例化调用语句注释掉,否则下面的链式调用不生效 (new Dog)->feeding('骨头')->hobby(',可爱,温顺,听话~~');
运行实例 »
点击 "运行实例" 按钮查看在线实例