Closed bwoebi closed 3 years ago
Good point. Maybe it would be easiest to make sure strict comparison (===
) will return true for unit cases even when they're not the same object? Which would not really be unit cases anymore in that case I guess.
I think we should strive to ensure singleton-ness … Otherwise we're going to break current assumptions like spl_object_id($a) === spl_object_id($b)
<=> $a === $b
What about cases with associated values? Wouldn't we want Option::Some(1) === Option::Some(1)
to return true
, even if they're not the same object? Technically it would be better for enums to be value types but that would require a lot more code changes.
An alternative possibility would be making cases with associated values also singleton. (storing a lookup-able reference internally) That would be really value type-like. I have no idea how well that would work out and instantiating still needs to be O(1) and not O(n) with n being the number of already instantiated objects of that type...
I think this needs to be specified better in the RFC. We don't have to worry about ADTs at this point. However even for unit enums this poses a challenge.
new
should probably be forbidden completely and thrownewInstanceWithoutConstructor
should probably also throwunserialize
should always return the same objectUpdated RFC to forbid new/newInstanceWithoutConstructor. Also updated it to just disallow serialization for now. If you can figure out how to support it, great, but better to forbid it outright than have it half-assed and broken.
Serialization: the class name (full class name with double colon) with empty object contents (unitary enums). Unserialization really just needs to look the "type" of the class up and branch accordingly, if enum fetch singleton object from the given constant, otherwise instantiation. I strongly oppose not supporting it.
Done, this now works.
What is $obj now? Does that throw? What about
new ReflectionClass(SomeEnum::SomeValue)->newInstanceWithoutConstructor();
? What about$obj = unserialize(serialize(SomeEnum::SomeValue));
Esp. the latter case should work I think, and return the singleton object.