DateTimeImmutable方法参数类型在运行时不被识别导致子类重写方法兼容错误的原因咨询
Great question! This behavior ties directly to how PHP handles built-in classes implemented in C versus user-defined PHP classes. Let’s break down the root causes:
Built-in class type hints are often documentation-only
Even though the PHP docs listDateIntervalas the parameter type forDateTimeImmutable::add(), this type hint isn’t enforced at the engine level for the C-implemented parent method. When you add an explicit type hint to your pure-PHP subclass, PHP’s method compatibility checker sees a mismatch—because the underlying C method’s signature doesn’t carry the type information PHP uses to validate subclass overrides.PHP’s compatibility rules treat built-in and user classes differently
For user-defined PHP classes, if a parent method has a parameter type hint, the subclass must match it exactly (or use a valid covariant type). But built-in classes bypass this rule: their methods live at a lower engine level, and PHP doesn’t recognize their documented type hints as part of the runtime method contract. Adding theDateIntervalhint to your subclass makes PHP think you’re altering the method’s signature in an incompatible way.Reflection reveals the runtime signature mismatch
If you use PHP’s reflection to inspectDateTimeImmutable::add(), you’ll notice the parameter has no explicit type hint registered in the runtime. That’s why your subclass’s type hint triggers an error—PHP can’t verify the parent method "should" accept aDateInterval, so it flags your override as breaking.
Fix for Your Code
As you discovered, removing the explicit type hint aligns your subclass method with the runtime signature of the parent, resolving the error:
class NullDateTime extends DateTimeImmutable { public function __construct() { parent::__construct(DateTimeUtil::NULL_DATETIME); } /** * {@inheritdoc} */ public function add($interval) {} }
This quirk isn’t unique to DateTimeImmutable—you’ll encounter the same issue with most built-in classes whose methods are documented with type hints but implemented in C.
内容的提问来源于stack exchange,提问作者Julius

