hack类型常量:Constraints
类型常量的约束(Constraints)类似于泛型类型参数的约束,因为它们限制类型常量可能被覆盖的内容。
抽象类
对抽象类型常量的约束要求任何覆盖抽象类型常量的类必须是约束类型的子类型。
<?hh
namespace Hack\UserDocumentation\TypeConstants\Constraints\Examples\AbsClass;
abstract class AbsParent {
abstract const type Foo as arraykey;
}
class FirstChild extends AbsParent {
const type Foo = string; // good since string is arraykey.
}
class SecondChild extends AbsParent {
const type Foo = float; // typechecker error since float is not an arraykey.
}
/***
abstract-type-errors.php:13:7,17: Class Hack\UserDocumentation\TypeConstants\Constraints\Examples\AbsClass\SecondChild does not correctly implement all required methods (Typing[4110])
abstract-type-errors.php:13:27,35: Some methods are incompatible with those declared in type Hack\UserDocumentation\TypeConstants\Constraints\Examples\AbsClass\AbsParent
Read the following to see why:
abstract-type-errors.php:6:23,25: Unable to satisfy constraint on this type constant
abstract-type-errors.php:6:30,37: This is an array key (int/string)
abstract-type-errors.php:14:20,24: It is incompatible with a float
***/
Concrete Classes
一个具体的类型常量必须有一个约束,以便任何孩子覆盖该类型的常量。
<?hh
namespace Hack\UserDocumentation\TypeConstants\Constraints\Examples\ConcClass;
class ParentWithConstraint {
const type Foo as arraykey = arraykey;
}
class Child extends ParentWithConstraint {
// good since string is arraykey and parent constrained to arraykey.
const type Foo = string;
}
class ParentWithoutConstraint {
const type Foo = arraykey;
}
class BadChild extends ParentWithoutConstraint {
// Although int is an arraykey, parent not constrained to arraykey, so this
// is a typechecker error.
const type Foo = int;
}
/***
concrete-type-errors.php:18:7,14: Class Hack\UserDocumentation\TypeConstants\Constraints\Examples\ConcClass\BadChild does not correctly implement all required methods (Typing[4110])
concrete-type-errors.php:18:24,46: Some methods are incompatible with those declared in type Hack\UserDocumentation\TypeConstants\Constraints\Examples\ConcClass\ParentWithoutConstraint
Read the following to see why:
concrete-type-errors.php:21:14,16: The assigned type of this type constant is inconsistent with its parent
concrete-type-errors.php:21:20,22: This is an int
concrete-type-errors.php:15:20,27: It is incompatible with an array key (int/string)
***/