• PHP 面向对象:方法重载


    如果从父类继承的方法不能满足子类的需求,可以对其进行改写,这个过程叫方法的覆盖(override),也称为方法的重载。

    当对父类的方法进行重写时,子类中的方法必须和父类中对应的方法具有相同的方法名称,在PHP5中不限制输入参数类型、参数数量和返回值类型。(这点和Java不同)。

    子类中的覆盖方法不能使用比父类中被覆盖方法更严格的访问权限。

    声明方法时,如果不定义访问权限。默认权限为public。

    PHP5重写方法

    先设置一个父类,这个父类是 “Dog”类,这个类描述了dog的特性。

    Dog有2个眼睛,会跑,会叫。就这样描述先。

    我养了一直狗,是只小狗,符合Dog类的特性,但有所不同。

    我的小狗有名字,我的小狗太小了,不会大声的叫,只会哼哼。

    我们用继承的概念去实现这个设计。

      <?
      // 狗有两只眼睛,会汪汪叫,会跑.
      class  Dog {
          protected  $eyeNumber =2; //属性
          //返回封装属性的方法.
          public function getEyeNumber(){
              return $this->eyeNumber;
          }
          //狗会叫  
          public function  yaff(){
              return  "Dog yaff, wang ..wang ..";
          }
          //狗会跑
          public function  run(){
              return  "Dog run..running ...";
          }
      }
      $dog = new Dog();
      echo "dog have ".$dog->getEyeNumber()." eyes. <br>";
      echo $dog->yaff() ."<br>".$dog->run();
      echo  "<br><br>";
      //这是我的小狗叫"狗狗",它很小.不会汪汪叫,只会哼哼哼..
      class MyDog extends Dog {
          private $name = "狗狗";
          public function getName(){
              return $this->name;
          }
          public function  yaff(){
              return  $this->name." yaff, heng...heng ..";
          }  
      }
      $myDog = new MyDog();
      echo $myDog->getName()." have ".$myDog->getEyeNumber()." eyes. <br>";
      echo $myDog->yaff() ."<br>".$myDog->run();
      ?>

    程序运行结果:

      dog have 2 eyes.
      Dog yaff, wang ..wang ..
      Dog run..running ...
       
      狗狗 have 2 eyes.
      狗狗 yaff, heng...heng ..
      Dog run..running ...

    重写方法与访问权限

    子类中的覆盖方法不能使用比父类中被覆盖方法更严格的访问权限。

    父类为public 子类为 private时。

      <?
      // 简化dog类和mydog类,演示重写的访问权限.
      class Dog {
          protected  $eyeNumber =2; //属性
          //返回封装属性的方法.
          public function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
       
      class MyDog extends Dog {
          protected function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
      /*
      class MyDog extends Dog {
          private function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
      */
       
      ?>

    程序运行结果:

      Fatal error: Access level to MyDog::getEyeNumber() must be public (as in class Dog) in E:\PHPProjects\test.php on line 15

    父类为public 子类为 protected时。

      <?
      // 简化dog类和mydog类,演示重写的访问权限.
      class Dog {
          protected  $eyeNumber =2; //属性
          //返回封装属性的方法.
          public function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
       
      class MyDog extends Dog {
          private function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
       
      ?>

    程序运行结果:

      Fatal error: Access level to MyDog::getEyeNumber() must be public (as in class Dog) in E:\PHPProjects\test.php on line 15

    重写时的参数数量

    子类可以拥有与父类不同的参数数量。(这点与java不同,PHP是弱类型语言。)

      <?
      // 简化dog类和mydog类,演示重写方法的参数.
      class  Dog {
          protected  $eyeNumber =2; //属性
          //返回封装属性的方法.
          public function getEyeNumber(){
              return $this->eyeNumber;
          }  
      }
      class MyDog extends Dog {
          //重写的方法与父类的方法有不同的参数数量.
          public function getEyeNumber($eys){
              $this->eyeNumber = $eys;
              return $this->eyeNumber;
          }  
      }
       
      $myDog = new MyDog();
      echo "my dog hava ".$myDog->getEyeNumber(3) ." eyes.";
      //啸天犬..哈..
      //下面这句会报一个丢失参数的错误.
      //echo "my dog hava ".$myDog->getEyeNumber() ." eyes.";
      ?>

    程序运行结果:

      my dog hava 3 eyes.

    构造函数重写

    下面这个例子中,父类和子类都有自己的构造函数,当子类被实例化时,子类的构造函数被调用,而父类的构造函数没有被调用,请对比第一节的构造函数继承。

      <?
      //2-2 / extends1.php
      //构造函数继承的问题.
      class Animal{
          public $legNum = 0;
          public function __construct(){
              $this->legNum = 4;
              echo "I am an animal<br>";
          }
      }
      class Dog1 extends Animal {
          public function __construct(){
              $this->legNum = 4;
              echo "I am a Dog .<br>";
          }
      }
      $dog1 = new Dog1();
      echo "<br>";
      echo  "legNum is ".$dog1->legNum;
      /*
      实例化子类时.构造函数被调用了.
      */
      ?>

    程序运行结果:

      I am a Dog .
       
      legNum is 4

    注:这点和Java不同,在java中构造函数是不能被继承的,而且子类实例化时,子类的构造函数被调用,父类的构造函数也会调用。

  • 相关阅读:
    node.js
    Ajax常见面试题
    CF932E Team Work
    斯特林数
    UOJ #62. 【UR #5】怎样跑得更快
    洛谷 P4593 【[TJOI2018]教科书般的亵渎】
    洛谷 P4321 【随机漫游】
    洛谷 P4707 【重返现世】
    洛谷 P3175 [HAOI2015]按位或
    CF Gym101933K King's Colors
  • 原文地址:https://www.cnblogs.com/firstdream/p/2424908.html
Copyright © 2020-2023  润新知