PHP 8.4.2 Released!

ReflectionClass::newLazyGhost

(PHP 8 >= 8.4.0)

ReflectionClass::newLazyGhostCreates a new lazy ghost instance

说明

public ReflectionClass::newLazyGhost(callable $initializer, int $options = 0): object

Creates a new lazy ghost instance of the class, attaching the initializer to it. The constructor is not called, and properties are not set to their default value. However, the object will be automatically initialized by invoking the initializer the first time its state is observed or modified. See Initialization Triggers and Initialization Sequence.

参数

initializer
The initializer is a callback with the following signature:

initializer(object $object): void
object
The object being initialized. At this point, the object is no longer marked as lazy, and accessing it does not trigger initialization again.

The initializer function must return null or no value.
options

options can be a combination of the following flags:

ReflectionClass::SKIP_INITIALIZATION_ON_SERIALIZE
By default, serializing a lazy object triggers its initialization. Setting this flag prevents initialization, allowing lazy objects to be serialized without being initialized.

返回值

Returns a lazy ghost instance. If the object has no properties, or if all its properties are static or virtual, a normal (non-lazy) instance is returned. See also Lifecycle of Lazy Objects.

错误/异常

An Error if the class is internal or extends an internal class except stdClass.

示例

示例 #1 Basic usage

<?php

class Example {
public function
__construct(public int $prop) {
echo
__METHOD__, "\n";
}
}

$reflector = new ReflectionClass(Example::class);
$object = $reflector->newLazyGhost(function (Example $object) {
$object->__construct(1);
});

var_dump($object);
var_dump($object instanceof Example);

// Triggers initialization, and fetches the property after that
var_dump($object->prop);

?>

以上示例会输出:

lazy ghost object(Example)#3 (0) {
  ["prop"]=>
  uninitialized(int)
}
bool(true)
Example::__construct
int(1)

参见

添加备注

用户贡献的备注 1 note

up
1
dave1010 at gmail dot com
26 days ago
Simple helper function that makes it easier to understand:

<?php

function createLazyGhost(
string $class,
?callable
$initializer = null,
?array
$propertySetterCallables = null
): object {
$reflection = new ReflectionClass($class);

return
$reflection->newLazyGhost(function (object $object) use ($initializer, $propertySetterCallables) {
// Initialize via the main initializer if provided
if ($initializer) {
$initializer($object);
}

// Set properties using the callables if provided
if ($propertySetterCallables) {
foreach (
$propertySetterCallables as $property => $callable) {
if (
is_callable($callable)) {
$object->$property = $callable();
}
}
}
});
}

?>

This supports using either a main object initializer and/or property initializers.

Here's an example, where generating order IDs and calculating totals is considered expensive, so we only do it when necessary:

<?php

class Order {
public
string $orderId = '';
public
float $total = 0.0;
}

$initializer = function (Order $order) {
$order->orderId = 'ORD12345';
};

$propertySetters = [
'total' => fn() => 200.75,
];

// Lazy ghost with both an initializer and property callables
$lazyOrder = createLazyGhost(Order::class, $initializer, $propertySetters);

// We can now use $lazyOrder as normal, even though the properties haven't been calculated yet.

// Do something that triggers initialization
echo $lazyOrder->orderId . PHP_EOL;
echo
$lazyOrder->total . PHP_EOL;

?>
To Top