PHP 接口(interface)实现拒绝参数的子类

标签 php interface subclass type-hinting interface-implementation

考虑一下:

class A{}

class B extends A{}

interface I{
 // expects object instanceof A
 function doSomething(A $a);
}

class C implements I
{
 // fails ????
 function doSomething(B $b){}
}

在我的概念中,上面应该工作,但它不作为 php 拒绝要求第一个参数与接口(interface) (I) 中定义的类型 (A) 完全相同的实现。由于 B 是 A 的子类,所以我看不出有什么问题。我在这里遗漏了什么吗?

最佳答案

class C implements I 意味着CI之间一定存在子类型关系。这意味着 C 类型的对象应该可以在任何需要 I 类型的对象的地方使用。

在您的情况下,CI 更具限制性,因为它对其 doSomething 参数有更精确的要求 -- I。 doSomething 适用于任何 AC.doSomething 需要 A

的特定子类型

请注意,如果您将 C.doSomething 更改为接受任何 A,那么没有什么可以阻止您将类型为 B 的对象传递给它。你不能只需要 B,因为那样你会破坏子类型契约(Contract)。

从理论上讲,子类型可以更自由地处理它们的函数参数,更具体地处理它们的返回类型(但反之亦然,就像你的情况一样)。在实践中,编程语言可能要求重写方法中的参数类型在所有地方都必须相同。

关于PHP 接口(interface)实现拒绝参数的子类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4782824/

相关文章:

python:哪里需要真正的内置文件对象?

Java 字典迭代器类型问题

design-patterns - 使用与域实体的一对一接口(interface)是好的还是坏的做法?为什么?

Java匿名子类和常规(非匿名)子类的区别

php - not in function PHP 中的多个条件

php - 使用php将文件中的信息导入到mysql

php - 根据外部请求在 Netbeans 中启动 XDebug

python - 在 Python 中扩展类时执行代码

c++ - 从用户定义的类/指向成员函数的指针子类化编辑控件

php - Doctrine 如何处理多个请求?