bis*_*hop 7 php liskov-substitution-principle
此LSP违规会引发致命错误:
abstract class AbstractService { }
abstract class AbstractFactory { abstract function make(AbstractService $s); }
class ConcreteService extends AbstractService { }
class ConcreteFactory extends AbstractFactory { function make(ConcreteService $s) {} }
Run Code Online (Sandbox Code Playgroud)
此LSP违规也会引发致命错误:
interface AbstractService { }
interface AbstractFactory { function make(AbstractService $s); }
class ConcreteService implements AbstractService { }
class ConcreteFactory implements AbstractFactory { function make(ConcreteService $s) {} }
Run Code Online (Sandbox Code Playgroud)
虽然这种LSP违规只会引发警告:
class Service { }
class Factory { function make(Service $s) {} }
class MyService extends Service { }
class MyFactory extends Factory { function make(MyService $s) {} }
Run Code Online (Sandbox Code Playgroud)
为什么?它们不应该都是致命的,因为它们都是逆变的吗?
在第一种情况下,这是一个致命的错误,因为PHP要求您与父抽象类兼容:
从抽象类继承时......方法的签名必须匹配.
在同样如此在第二种情况:
实现接口的类必须使用与接口中定义的完全相同的方法签名.不这样做会导致致命错误.
在第三种情况下,您扩展了普通的PHP类,而不是抽象的.PHP允许您更改签名,尽管有警告.
这显然不是一个好习惯,并且如你所指出的那样违反了LSP.这只是PHP为您提供尖锐物体的众多方式之一,如果您不小心,会让您自己受伤.=)
如果要强制执行LSP,则需要使用接口,抽象或final
在父类中创建方法.
以下是一个示例final
:https://3v4l.org/s42XG
归档时间: |
|
查看次数: |
338 次 |
最近记录: |