严格的标准:声明“”应与“”兼容


Strict Standards: Declaration of ' ' should be compatible with ' '

我刚刚在PHP 5.4上安装了woocommerce 2.0(在Wordpress上(,我得到了这个:

严格的标准:申报WC_Gateway_BACS::p付款(( 应该与 WC_Payment_Gateway::p rocess_payment(( 兼容 D:''my''path''to''htdocs''wordpress''plugins''woocommerce''classes''gateways''bacs''class-wc-gateway-bacs.php 在线。。。

我检查了文件,发现WC_Payment_Gateway没有方法process_payment().我需要知道如何解决这个问题(不是通过设置 error_reporting() (。

PHP 中的严格标准到底是什么?
在什么情况下我们得到这个错误?

WC_Payment_Gatewayabstract-wc-payment-gateway.php中定义并声明了一个方法

function process_payment() {}

WC_Gateway_BACS将其定义为

function process_payment( $order_id ) { ...

(也许你混淆了WC_Payment_Gateway和WC_Payment_Gateways(。

因此,不同的签名(0 个参数与 1 个参数(->严格的错误。
由于似乎*总是与一个参数一起使用,因此您可以更改

function process_payment() {}

function process_payment($order_id) {}

(*(请记住,我从最后五分钟才知道woocommerce,所以不要相信我的话。

引自PHP手册

在 PHP 5 中,可以使用新的错误级别E_STRICT。在 PHP 5.4.0 之前,E_STRICT 不包含在 E_ALL 中>,因此您必须在>PHP <5.4.0 中显式启用此类错误级别。在开发过程中启用E_STRICT有一些好处。STRICT 消息>提供有助于确保代码的最佳互操作性和转发>兼容性的建议。这些消息可能包括静态调用非静态>方法,在兼容的类定义中定义属性,同时在>使用的特征中定义,并且在 PHP 5.3 之前,一些不推荐使用的功能会发出E_STRICT错误>例如在实例化时通过引用分配对象。

您收到此错误是因为WC_Gateway_BACS::p rocess_payment(( 声明与 WC_Payment_Gateway::p rocess_payment(( 不同(可能不是相同数量的参数等(。如果WC_Payment_Gateway没有方法process_payment,请检查它的父类:)

此外,如果要禁用 STRICT 错误,请将 ^ E_STRICT添加到错误报告配置中,例如:

error_reporting(E_ALL ^ E_STRICT);

如果你想在不关闭任何错误的情况下保留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();
        // ...
    }
}

当您在父类和子类中使用相同的函数时,但子类需要参数而父类不需要参数,您将收到Strict Standards错误。

经理:

public function getAtPosition($position)
{
    foreach ($this->getList() as $obj)
    {
        if ($obj->getPosition() == $position)
            return $obj;
    }
    return null;
}

菜单管理器扩展管理器:

public function getAtPosition($position, $parent)
{
    foreach ($this->getList() as $m)
    {
        if ($m->getParent() == $parent && $m->getPosition() == $position)
            return $m;
    }
    return null;
}

此示例将生成一个错误:

严格的标准:MenuManager::getAtPosition(( 的声明应该 与管理器兼容::getAtPosition($position(

因为我们对函数没有相同的参数,

所以让我们欺骗它并添加参数,即使我们没有使用它们!

经理:

public function getAtPosition($position, $dummy = 0) // Dummy to avoid Strict standards errors
{
    foreach ($this->getList() as $obj)
    {
        if ($obj->getPosition() == $position)
            return $obj;
    }
    return null;
}

菜单管理器扩展管理器:

public function getAtPosition($position, $parent = 0)
{
    foreach ($this->getList() as $m)
    {
        if ($m->getParent() == $parent && $m->getPosition() == $position)
            return $m;
    }
    return null;
}

唯一需要注意的是,当使用 MenuManager.class.phpgetAtPosition()时,请确保您实际上正在发送 2 个参数,因为我们必须声明 $parent = 0 以匹配父级的声明。

每个扩展Manager且不包含getAtPosition()的类都将使用 Manager 中的方法。

如果在子类中声明,php 将使用子类中的方法而不是父类的方法。PHP 中没有overloading,所以我就是这样解决它的,直到它被正确实现。

这是一个更好的答案 - https://stackoverflow.com/a/9243127/2165415

例如
parentClass::customMethod($thing = false)
childClass::customMethod($thing)
因此,当您为类调用 customMethod() 时,它可能会触发错误,因为子方法尚未为第一个参数定义默认值。