Hi Larry, I admit that this flag is not too interesting, but I believe it still has its own merit. I can imagine that the flag could play well with property accessors as well, however, in my opinion, the main use-case of final properties generally doesn't involve setters/set accessors.
> In that case, "final" or "lazy" or "locked" would be reasonable names; read-only and immutable are misleading, as it's really write-once, not read-only, not truly immutable. In the meanwhile, I realized that - "immutable" is simply not true in case of resource and (non-immutable) object properties - "readonly" is probably somewhat better, but still not always true in case of lazy initialization - "final" seems ok, but it would probably be a better fit for a feature that would prevent a property to be overwritten (similarly to "final" for methods) So I think "final" should only be chosen if we don't want to restrict property overwriting later. Otherwise, we could use also "locked" or "sealed" (inspiring from C#). > As for references and untyped final properties... Just don't go there. Require a final property to be non-reference and typed. So it's essentially what Marco also suggested... Unfortunately, I didn't exactly get the idea first (I focused too much on the mixed type), but restricting final to typed properties now seems reasonable. :) But let me collect the possibilities that I've thought about so far: - do not implicitly initialize untyped final properties: although I liked this idea first, now it feels a bit unintuitive - add support for mixed, and implicitly convert untyped final properties to this type: unintuitive - require final properties to be explicitly initialized before object instantiation finishes: complicated, makes lazy initalization/proxying difficult/impossible - require final properties to be typed: looks straightforward > I do not foresee untyped properties ever going away Although I tend to declare types everywhere I can, I also believe we should leave gradual typing intact. Thank you very much for the feedback! Máté Kocsis Larry Garfield <la...@garfieldtech.com> ezt írta (időpont: 2020. febr. 15., Szo, 9:18): > On Fri, Feb 14, 2020, at 7:22 AM, Máté Kocsis wrote: > > Hi Internals, > > > > I'd like to propose the idea of adding support for > immutable/final/readonly > > properties in PHP 8. > > > > My plan is to add a new immutable/final/readonly (the name is up for > > debate) property modifier to the language so that these kind of > properties > > could only be initialized but not modified afterwards. Unlike how final > > properties in Java work, I think it would be beneficial to allow lazy > > initialization of these properties after object construction have taken > > place. Currently, I'm in favour of using final or readonly, but not yet > > very sure. > > > > I'll write a proper RFC in the following days/week. My clear intent with > > final properties is to pave the road for immutable objects for which I > have > > a POC pull request open (but I haven't pushed all my work yet). > > > > So far, my biggest question (apart from the name) have been how non-typed > > properties should behave: as they are implicitly initialized to null if > > they don't have an explicit default value (while typed properties remain > > uninitialized), further modifications would be impossible to do on them - > > which would make non-typed final properties almost useless. Nikita > > suggested to just avoid their initialization, but I'd be curious about > > other ideas as well. > > > > Thanks, > > Máté Kocsis > > My concern is that a simple read-only/final "flag" is a very limited > feature set. I'd still love for us to revisit property accessors at some > point (if the performance issues could be resolved), and I fear that > layering that *and* a read-only flag together would result in... much > complex weirdness. (Technical term.) > > That said, were such a feature to be added, I would strongly recommend > making them able to be defined in terms of an expression, or possibly a > callable/anon function, with no explicit setting allowed. To wit: > > class Foo { > > protected string $firstName; > protected string $lastName; > > protected function getFullName() { return $this->firstName . > $this->lastName; } > > // And then one of these options: > > public final string $fullName = $this->firstName . $this->lastName; > > public final string $fullName = fn() => $this->firstName . > $this->lastName; > > public final string $fullName = $this->getFullName(); > } > > That would allow for their complete definition in one location, make it > clear how they're derived, etc. They essentially become an auto-memoizing > method (which suits me just fine). Their value would potentially change > depending on when it's first called depending on the other values in the > object, but that's no different than if they were simply "set" from an > arbitrary location. The potential for unpredictable semi-non-determinism > is the same, or possibly better this way. > > (In that case, "final" or "lazy" or "locked" would be reasonable names; > read-only and immutable are misleading, as it's really write-once, not > read-only, not truly immutable. I suppose then an "immutable object" would > be one in which all properties are either final/lazy/locked or set by the > constructor only.) > > There was a thread a few weeks ago on "lazily derived constants" that > probably has some interesting thoughts as well, though of course this would > be property-like syntax, which is fine. > > As for references and untyped final properties... Just don't go there. > Require a final property to be non-reference and typed. I do not foresee > untyped properties ever going away (too much legacy code, plus they are > legit useful at times), but that doesn't mean every conceivable property > variant ever needs to support them. Requiring that a final property be > typed non-reference seems entirely reasonable to me. > > --Larry Garfield > > -- > PHP Internals - PHP Runtime Development Mailing List > To unsubscribe, visit: http://www.php.net/unsub.php > >