概述
类中的某些成员如何才能被其他类使用呢?使用继承的话,这继承链也太长了,为了方便,php提供了代码复用技术trait。
1.定义:Trait
是为类似 PHP 的单继承语言
而准备的一种代码复用机制。trait可以使得单继承语言摆脱
为了复用,而不得不继承的尴尬处境,让面向对象
变得更加纯粹。
2.基础语法:
trait是一种类似class
的关键字。
<?php
trait Eat{
public $a=10; //trait内允许有类的成员属性(包括静态属性),成员方法(包括静态方法)
public static $b=666;
//const c=3.14; //trait内不允许有常量
protected $e; //允许定义,但是实际不用
private $f;
public function getA()
{
echo $this->a,"<br>";
}
public static function getB()
{
echo self::$b,"<br>";
}
}
?>
登录后复制
trait
是用来实现代码的复用的,不可以被实例化也不可以被继承(因为根本不是类)。
<?php
trait Eat{}
// $a=new Eat;//报错
//calss A extends Eat{}//报错
?>
登录后复制
3.trait的使用
trait只是一段代码的集合,使用时必须要使用use
进行引用。
<?php
trait Eat{
public $a=10;
public static $b=666;
//const c=3.14;
public function getA()
{
echo $this->a,"<br>";
}
public static function getB()
{
echo self::$b,"<br>";
}
}
class A{
use Eat;
public function getC()
{
echo $this->a,"<br>";
}
}
$boy=new A();
$boy->getC();
$boy->getA();
$boy->getB();
?>
登录后复制
一个类可以使用多个trait。
<?php
trait A1{
}
trait A2{
}
class People{
use A1,A2;
}
?>
登录后复制
4.trait使用的问题
a.如果同时引入的多个trait中有同名属性,那么会产生冲突。
<?php
trait A1{
public $a=11;
}
trait A2{
public $a=22;
}
class A3{
use A1,A2;//不允许同名属性
public function geta(){
echo $this->a;
}
}
$example=new A3();
?>
登录后复制
b.如果同时引入的多个trait中有同名方法,那么会产生冲突,有两种方案解决如A3、A4。
<?php
trait A1{
public $a=11;
public function eat(){
echo "A1中eat()方法","<br>";
}
}
trait A2{
public $b=22;
public function eat(){
echo "A2中eat()方法","<br>";
}
}
class A3{
use A1,A2{
A1::eat insteadOf A2; //A1中的eat替代A2中的eat
}
}
class A4{
use A1,A2{
A1::eat insteadOf A2;//A1中的eat替代A2中的eat
A2::eat as eat2; //A2中的eat取别名eat2
}
}
$example=new A3();
$example->eat();
$example=new A4();
$example->eat2();
?>
登录后复制
c.同名覆盖问题:如果类中有与引入的trait同名成员,会有不同处理:
属性:不允许重名,即类中不允许定义与trait中同名的成员属性(静态属性也一样)。
方法:类覆盖trait。
d.继承覆盖问题:如果类中在使用trait
的同时,也是继承自父类,而trait中与父类中有同名方法,那么trait
中将覆盖父类同名方法;如果要访问父类方法,可以在trait同名方法中使用parent
关键字访问父类同名方法。
<?php
trait Eat{
public function eat(){
echo 'Eat::eat';
}
}
class Human{
public function eat(){
echo 'Human::eat';
}
}
//子类继承父类同时使用trait
class Man extends Human{
use Eat;
}
$m = new Man();
$m->eat();
?>
登录后复制
e.trait自己不能访问,只是用来给其他类提供代码复用的,因此允许类在使用trait时,使用更高的访问控制权:在as
之后,使用目标访问修饰限定符。
<?php
trait Eat{
private function show(){
echo 'eat';
}
}
class Human{
use Eat{
show as public eshow;
//注意:as是用来设定别名的,虽然没有同名show,但是系统认为show已经存在,所以必须别名,权限的更改的方法不是
//本尊
}
}
$h = new Human();
$h->eshow(); //eat
?>
登录后复制
f.trait中可以使用抽象方法
,使用类必须实现对应抽象方法
:使用类要么为抽象类,要么就必须实现抽象方法。
<?php
trait Eat{
public function eat(); //抽象方法
}
abstract class Human{
use Eat; //抽象类:可以不实现抽象方法
}
class Animal{
use Eat;
public function eat(){ //具体类:实现抽象方法
echo 'Animal::eat';
}
}
?>
登录后复制
推荐:php教程,php视频教程
以上就是总是在重复,气抖冷,trait何时才能站起来?的详细内容,更多请关注靠谱客其它相关文章!
最后
以上就是含蓄香菇为你收集整理的总是在重复,气抖冷,trait何时才能站起来?的全部内容,希望文章能够帮你解决总是在重复,气抖冷,trait何时才能站起来?所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复