本文共 913 字,大约阅读时间需要 3 分钟。
在Hack的代码之间,继承是更加复杂的相互关系中的一种。这复杂性主要来自于当继承关系被创建时,继承和被继承的代码之间的分离现象。举例来说,如果你有个类型标注为SomeClass的对象并可以调用这个对象的某个方法,那么你可以调用继承自SomeClass的任何类的某个方法。这个调用仍然需要是类型安全的,这就意味着覆盖其他方法的时候,方法的类型必须有一定的规则。
在一个覆盖方法中,参数类型必须和被覆盖的方法类型完全一致。这主要是因为继承自PHP的一个行为。在PHP中,任何覆盖自抽象方法或者接口中声明的覆盖方法,都必须精确地匹配被覆盖方法的参数类型。这在未来Hack版本中的声明可能会有所改变,允许改变方法的参数类型将是更通常的做法。换句话说,当进行方法覆盖时,覆盖方法的返回类型并不一定保持相同,相对于被覆盖的方法而言,覆盖方法可以有一个更加明确的返回类型。例如:class ParentClass { public function generate(): num { // ... } }class ChildClass extends ParentClass { public function generate(): int { // OK // ... } }
虽然改变了返回类型,这种多态的调用仍然是类型安全的。
function f(ParentClass $obj) { $number = $obj->generate(); // 即使$obj是个ChildClass实例,generate()方法自然会返回num类型 // 因为ChildClass::generate() 返回的是int类型,而所有int类型都属于num类型用更通常的返回类型进行覆盖是非法的。例如,如果ChildClass的generate()方法被声明成返回类型为mixed的话,类型检查器将会报告错误。转载地址:http://schax.baihongyu.com/