PHP 7.3.x 中的已知错误与单例子类化?

问题描述

使用单例子类化,我得到一个

致命错误:TheChild::getInstance() 的声明:TheChild must be compatible with TheParent::getInstance(): TheParent in ..\test.PHP on line 36

使用 PHP 7.4.x NTS x64 一切正常。
使用 PHP 8.0.x NTS x64 也很好。
PHP 7.3.x NTS x64 是坏孩子。

这是我的代码

error_reporting(E_ALL);

class TheParent {
    private static $instance;

    private function __construct() {
        // ...
    }

    public static function getInstance(): self {
        if (self::$instance == null) {
            self::$instance = new self();
        }
        return self::$instance;
    }
}

class TheChild extends TheParent {
    private static $instance;

    private function __construct() {
        parent::__construct();
        // ...
    }

    public static function getInstance(): self {
        if (self::$instance == null) {
            self::$instance = new self();
        }
        return self::$instance;
    }
}

我只是不确定,我在这里遗漏了什么......有人有任何见解吗?客户使用 7.3.x,所以我坚持使用。

解决方法

不是错误...

PHP 7.4 引入(完全)支持协变返回类型(还有逆变参数,但这超出了您的问题范围)。 https://www.php.net/manual/en/language.oop5.variance.php

父类中的

self 与子类中的 self 不同,这就是为什么它在 PHP 7.3(及以下)中不起作用,但在 7.4(及以上)中有效) 因为上述协方差(子类的 self 是父类 self 的更具体版本)。


话虽如此,子类中不需要重复getInstance()方法,所以这不是一个实际问题。


此外,您可能还想了解后期静态绑定:https://www.php.net/manual/en/language.oop5.late-static-bindings.php