PHP trait用法

自 PHP 5.4.0 起,PHP 实现了一种代码复用的方法,称为 trait。

Trait 是为类似 PHP 的单继承语言而准备的一种代码复用机制。Trait 为了减少单继承语言的限制,使开发人员能够自由地在不同层次结构内独立的类中复用 method。Trait 和 Class 组合的语义定义了一种减少复杂性的方式

Trait 和 Class 相似,但仅仅旨在用细粒度和一致的方式来组合功能。 无法通过 trait 自身来实例化。它为传统继承增加了水平特性的组合;也就是说,应用的几个 Class 之间不需要继承。

trait关键字定义的内容是不能被实例化和继承的。

优先级

本类中的方法会覆盖Trait中的方法, 而Trait中的方法会覆盖子类中的方法。 基类 > Trait > 子类

代码示例:

namespace Design;


trait Hello
{
    public function world()
    {
        echo 'Hello from trait Hello';
    }
}

class MyHello {

    public function world(){
        echo 'Hello from MyHello';
    }
}

class SubHello extends MyHello {
    use Hello;

    public function world()
    {
        echo 'Hello from subHello';
    }
}

$hello = new SubHello();
$hello->world(); //输出Hello from trait Hello

$hello = new MyHello();
$hello->world(); //输出 Hello from MyHello

多个Trait用法

引用多个Trait的时候,用【,】隔开,这样就可以引用多个Trait

trait Hey{
    public function sayHey()
    {
        echo 'Hey';
    }
}
trait You{
    public function sayYou()
    {
        echo ' you';
    }
}

class heyYou{
    use Hey,You;

    public function sayEnd()
    {
        echo '!!!!';
    }
}
$say = new heyYou();
$say->sayHey();
$say->sayYou();
$say->sayEnd();
//输出Hey you!!!!

遇见冲突的情况

多个trait的时候,会出现每个trait里面有相同的方法, 这时候执行的时候会报错:


Fatal error: Trait method talkA has not been applied, because there are collisions with other trait methods on Design\AB in Traint.php on line 108

这种情况下如何解决呢?这时候需要使用 insteadof 操作符来明确指定使用冲突方法中的哪一个:代码示例

trait A
{
    public function talkA()
    {
        echo 'A->talkA';
    }

    public function talkB()
    {
        echo 'A->talkB';
    }
}

trait B
{
    public function talkA()
    {
        echo 'B->talkA';
    }

    public function talkB()
    {
        echo 'B->talkB';

    }
}

class AB{
    use A,B{
        A::talkB insteadof B;
        B::talkA insteadof A;
    }
}
$ab = new AB();
$ab->talkA();
echo '<br>';
$ab->talkB();
//输出 B->talkA
//     A->talkB

 

 

0

发表评论

电子邮件地址不会被公开。