PHP:如果我以非静态方式调用静态方法怎么办?

Far*_* Rn 22 php static-methods

我不是面向对象编程的专家,我有一个愚蠢的问题:

class test {
    public static function doSomething($arg) {
        $foo = 'I ate your ' . $arg;
        return $foo;
    }
}
Run Code Online (Sandbox Code Playgroud)

所以调用doSomething()方法的正确方法是做test::doSomething('Pizza');,我是对的吗?

现在,如果我这样称呼会发生什么:

$test = new test;
$bar = $test->doSomething('Sandwich');
Run Code Online (Sandbox Code Playgroud)

我已经测试了它并且没有任何错误或通知等工作但是这样做是否正确?

小智 16

正如Baba已经指出的那样,它会导致E_STRICT您的配置.

但即使这对您来说没有问题,我认为值得一提的是,以非静态方式调用静态方法可能会导致一些陷阱.

如果你有一个类层次结构

class A {
    public static function sayHello() {
        echo "Hello from A!\n";
    }

    public function sayHelloNonStaticWithSelf() {
        return self::sayHello();
    }

    public function sayHelloNonStaticWithStatic() {
        return static::sayHello();
    }
}

class B extends A {
    public static function sayHello() {
        echo "Hello from B!\n";
    }

    public function callHelloInMultipleDifferentWays() {
        A::sayHello();
        B::sayHello();
        $this->sayHelloNonStaticWithSelf();
        $this->sayHelloNonStaticWithStatic();
        $this->sayHello();
    }
}

$b = new B();
$b->callHelloInMultipleDifferentWays();
Run Code Online (Sandbox Code Playgroud)

这会产生以下输出:

Hello from A!
// A::sayHello() - obvious

Hello from B!
// B::sayHello() - obvious

Hello from A!
// $this->sayHelloNonStaticWithSelf()
// self alweays refers to the class it is used in

Hello from B!
// $this->sayHelloNonStaticWithStatic()
// static always refers to the class it is called from at runtime

Hello from B!
// $this->sayHello() - obvious
Run Code Online (Sandbox Code Playgroud)

如您所见,在混合静态和非静态方法调用和技术时,很容易实现意外行为.

因此,我的建议是:使用Class :: method显式调用您要调用的静态方法.或者更好的是根本不使用静态方法,因为它们使代码不可测试.