代码之家  ›  专栏  ›  技术社区  ›  waiwai933

方法声明应该与PHP中的父方法兼容

  •  95
  • waiwai933  · 技术社区  · 15 年前
    Strict Standards: Declaration of childClass::customMethod() should be compatible with that of parentClass::customMethod()
    

    兼容的 ?

    4 回复  |  直到 15 年前
        1
  •  129
  •   davidtbernal    15 年前

    childClass::customMethod() 具有不同的参数,或者访问级别(public/private/protected)不同于 parentClass::customMethod()

        2
  •  37
  •   ldrut    13 年前

    此消息意味着某些可能的方法调用可能在运行时失败。假设你有

    class A { public function foo($a = 1) {;}}
    class B extends A { public function foo($a) {;}}
    function bar(A $a) {$a->foo();}
    

    编译器只检查调用$a->foo()不需要参数$但是,a可能是需要参数的类B的对象,因此在运行时调用将失败。

    但是,这永远不会失败,也不会触发错误

    class A { public function foo($a) {;}}
    class B extends A { public function foo($a = 1) {;}}
    function bar(A $a) {$a->foo();}
    

    因此,没有一个方法可能比其父方法具有更多必需的参数。

    当类型提示不匹配时,也会生成相同的消息,但在这种情况下,PHP的限制更大。这会产生一个错误:

    class A { public function foo(StdClass $a) {;}}
    class B extends A { public function foo($a) {;}}
    

    class A { public function foo($a) {;}}
    class B extends A { public function foo(StdClass $a) {;}}
    

    这似乎比它需要的更严格,我认为这是由于内部。

    可见性差异会导致不同的错误,但基本原因相同。任何方法都不能比其父方法更不可见。

        3
  •  24
  •   Sajjad Shirazi    10 年前

    如果要保持OOP窗体而不关闭任何错误,还可以:

    class A
    {
        public function foo() {
            ;
        }
    }
    class B extends A
    {
        /*instead of : 
        public function foo($a, $b, $c) {*/
        public function foo() {
            list($a, $b, $c) = func_get_args();
            // ...
    
        }
    }
    
        4
  •  2
  •   Spholt    8 年前

    use Bar;
    
    interface A
    {
        public function foo(Bar $b);
    }
    

    B类

    class B implements A
    {
        public function foo(Bar $b);
    }
    

    如果你忘了包括 use

        5
  •  0
  •   Ferran    5 年前

    我在尝试从GitHub扩展现有类时遇到了这个问题。我要试着解释我自己,先写我认为应该写的课,然后写现在的课。

    我怎么想的

    namespace mycompany\CutreApi;
    
    use mycompany\CutreApi\ClassOfVendor;
    
    class CutreApi extends \vendor\AwesomeApi\AwesomeApi
    {
       public function whatever(): ClassOfVendor
       {
            return new ClassOfVendor();
       }
    }
    

    我终于做了什么

    namespace mycompany\CutreApi;
    
    use \vendor\AwesomeApi\ClassOfVendor;
    
    class CutreApi extends \vendor\AwesomeApi\AwesomeApi
    {
       public function whatever(): ClassOfVendor
       {
            return new \mycompany\CutreApi\ClassOfVendor();
       }
    }
    

    因此,当您使用返回名称空间类的方法,并且您尝试返回相同的类但使用其他名称空间时,似乎也会出现此错误。幸运的是,我已经找到了这个解决方案,但我并不完全理解PHP7.2中这个特性的好处,对我来说,根据需要重写现有的类方法是正常的,包括重新定义输入参数和/或甚至方法的行为。

    以前的方法的一个缺点是IDE无法识别\mycompany\CutreApi\ClassOfVendor()中实现的新方法。所以,现在,我将继续这个实现。

    当前完成

    namespace mycompany\CutreApi;
    
    use mycompany\CutreApi\ClassOfVendor;
    
    class CutreApi extends \vendor\AwesomeApi\AwesomeApi
    {
       public function getWhatever(): ClassOfVendor
       {
            return new ClassOfVendor();
       }
    }
    

    希望这能帮到别人。