On 27/05/2021 13:07, Pierre wrote:
So, if it's going to be used and abused in those magic APIs we all use daily without thinking about it (let's say, hydrators or serializers, dependency injection containers and all that stuff, and you do maintain some if I recall) and unlock some performance optimizations in there, I'd say go for it.


I think "abused" is the right word here. The uninitialized state exists in the first place because we don't have a way to enforce initialization in constructors, not because we really wanted a new special value that is "like null, but even more so".

The combination of union types and enums actually gives a much more expressive way of representing "valid value or explicit null or special default". To use the ORM lazy-loading example:


enum ORMState {
    case Unloaded;
}

class Example {
    private int|ORMState|null $foo = ORMState::Unloaded;

    public function getFoo(): ?int {
        if ( $this->foo === ORMState::Unloaded ) {
            $this->foo = $this->loadFromDatabase('foo');
        }
        return $this->foo;
    }

    private function loadFromDatabase($fieldName): ?int {
        echo "Fetching '$fieldName' from database...\n";
        return 42;
    }
}

// Create object; note there's no constructor, but the property has a default so is never uninitialized
$obj = new Example;
// On first call to method, the default value is detected and the property lazy-loaded
var_dump($obj->getFoo());
// Subsequent accesses return the loaded value directly, at the cost of a single strict comparison, no magic function needed
var_dump($obj->getFoo());


Unlike abusing "uninitialized" as a third state (next to int and null), this allows any number of states to be recorded, and treated appropriately. For instance, an auto-increment key might default to ORMState::NotYetCalculated, and trigger an error rather than a lazy-load.


Regards,

--
Rowan Tommins
[IMSoP]

--
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: https://www.php.net/unsub.php

Reply via email to