博客列表 >PHP面向对象联合编程

PHP面向对象联合编程

Jason
Jason原创
2020年05月04日 09:09:48703浏览

php之trait

trait同名方法解决方案

当我们引用两个trait,且他们有中有一个方法同名,这是就会产生冲突,那如何解决这种冲突呢

1.替代法

将其中一个用另一个代替,这样就不会产生冲突了

示例:

  1. trait tDemo1{
  2. public function hello()
  3. {
  4. echo 'hello';
  5. }
  6. }
  7. trait tDemo2{
  8. public function hello()
  9. {
  10. echo 'the world';
  11. }
  12. }
  13. trait tDemo3{
  14. use tDemo1,tDemo2{
  15. // 1.替代,将tDemo1的hello替代tDemo2的方法
  16. // 这样,在调用tDemo2的时候,就会用tDemo1代替执行
  17. tDemo1::hello insteadof tDemo2;
  18. }
  19. }
  20. class Work
  21. {
  22. use tDemo3;
  23. }
  24. $work = new Work();
  25. echo $work->hello();
  26. echo '<hr>';

2.别名法

将其中一个方法,给它起一个别名,调用的时候用别名,名称不会冲突,也是一种方法

示例

  1. trait tDemo1
  2. {
  3. public function hello()
  4. {
  5. echo 'hello';
  6. }
  7. }
  8. trait tDemo2
  9. {
  10. public function hello()
  11. {
  12. echo 'the world';
  13. }
  14. }
  15. trait tDemo3
  16. {
  17. use tDemo1,tDemo2{
  18. // 2.别名法,将tDemo2的hello用一个其他名字代替
  19. // 这样,在调用tDemo2的时候,就可以用别名调用
  20. tDemo2::hello as say;
  21. }
  22. }
  23. class Work
  24. {
  25. use tDemo3;
  26. }
  27. $work = new Work();
  28. echo $work->say();
  29. echo '<hr>';

如何在trait中改变trait中的访问控制

当在trait中引用了另外一个trait,且这个trait不被别人调用时,这时就出现了trait访问控制,分别是public ,protected ,private 这三个

示例

  1. trait tDemo1
  2. {
  3. public function hello()
  4. {
  5. echo 'hello1';
  6. }
  7. }
  8. trait tDemo2
  9. {
  10. public function hello()
  11. {
  12. echo 'hello2';
  13. }
  14. }
  15. trait tDemo3
  16. {
  17. use tDemo1,tDemo2{
  18. // tDemo1::hello as say;
  19. tDemo1::hello insteadOf tDemo2;
  20. tDemo2::hello as book;
  21. }
  22. // 通过`as`可以修改trait成员的访问控制,
  23. // public:表示可以访问
  24. // protected:不可访问
  25. // 将tHello中的hello方法设为保护的
  26. // use tDemo2 {hello as public;}
  27. }
  28. class Work
  29. {
  30. use tDemo3;
  31. }
  32. $work = new Work();
  33. echo $work->hello();
  34. // 此时无法调用,因为hello方法已经成为受保护的了
  35. echo $work->book();

trait实现接口的优点是什么?还有什么缺点?

优点

先就从trait说起,Trait是一种代码复用技术,为PHP的单继承限制提供一套灵活的代码复用机制。再讲接口的优点,接口主要的优点就是多态,还有多继承,一个接口,可以让具有继承关系的不同类对象,可以对相同名称的成员调用,产生不同的反应结果。一个类还可以继承多个接口,那么trait实现接口的优点就出来了,实现模块坏开发,当一个类继承多个接口,用trait将每个模块实现,代码复用就体现出来了。写的代码会非常的优雅。

缺点

用trait实现接口,有几个缺点

  • 一、同名方法优先级,用trait实现接口特别要注意优先级,当类中的方法与trait中的方法重名时,优先级的关系需要搞清楚。
  • 二、继承上下文中,具有优先级,trait在子类中优先级大于父类,也就是当父类中的方法与trait重名时,trait的权重大于父类

联合编程

示例

  1. // 随机输出一个用户的级别以及优惠力度
  2. $Data = [
  3. ['id' => '1','name' => '张三','level' => 'normalUser'],
  4. ['id' => '2','name' => '李四','level' => 'vipUser'],
  5. ['id' => '3','name' => '王麻子','level' => 'newUser'],
  6. ];
  7. interface iUserData
  8. {
  9. public static function generateId(int $min , int $max):int;
  10. }
  11. trait iPrint
  12. {
  13. static public function printLevel($level)
  14. {
  15. if($level == 'normalUser'):
  16. echo '普通用户'.'<br>';
  17. elseif ($level == 'vipUser' ):
  18. echo 'VIP用户'.'<br>';
  19. elseif ($level == 'newUser'):
  20. echo '新用户'.'<br>';
  21. else:
  22. echo '用户不存在'.'<br>';
  23. endif;
  24. }
  25. }
  26. trait iCreateId1
  27. {
  28. public static function generateId(int $min , int $max):int
  29. {
  30. return mt_rand($min,$max);
  31. }
  32. }
  33. // abstract class Discount implements iUserData
  34. abstract class Discount implements iUserData
  35. {
  36. use iCreateId1;
  37. public static function discount1($level)
  38. {
  39. if($level == 'normalUser'):
  40. echo '九折'.'<br>';
  41. elseif ($level == 'vipUser'):
  42. echo '七折'.'<br>';
  43. elseif ($level == 'newUser'):
  44. echo '八折'.'<br>';
  45. endif;
  46. }
  47. }
  48. // 工作类:输出类
  49. class User extends Discount
  50. {
  51. use iCreateId1,iPrint;
  52. public static function awrad(array $Data,int $id)
  53. {
  54. echo '用户名称为'.$Data[$id]['name'].'<br>';
  55. }
  56. }
  57. $id = User::generateId(0,2);
  58. $user = User::printLevel($Data[$id]['level']);
  59. $userdata = User::discount1($Data[$id]['level']);
  60. $userdata1 = User::awrad($Data,$id);

输出:

  1. 新用户
  2. 八折
  3. 用户名称为王麻子

总结

这个案例看似简单,如果用循环控制语句,可能几行代码就实现出来了,但是用面向对象实现出来,并不会那么简单,首先得知道数组的结构,以及函数传参,再用trait把它们是实现一个功能模块。用抽象类实现接口的好处就是,可以只实现其中的一个方法,而不用像继承类那样,把全部的都要实现。

声明:本文内容转载自脚本之家,由网友自发贡献,版权归原作者所有,如您发现涉嫌抄袭侵权,请联系admin@php.cn 核实处理。
全部评论
文明上网理性发言,请遵守新闻评论服务协议