On Apr 27, 2020, at 2:00 PM, Dan Smith <daniel.sm...@oracle.com> wrote: > > >> On Apr 24, 2020, at 3:34 PM, John Rose <john.r.r...@oracle.com> wrote: >> >> On Apr 24, 2020, at 12:43 PM, Dan Smith <daniel.sm...@oracle.com> wrote: >>> >>>> On Apr 24, 2020, at 1:32 PM, Remi Forax <fo...@univ-mlv.fr> wrote: >>>> >>>>> (Which, in hindsight, might have been a good rule for _all_ constructors, >>>>> if there was another way to initialize the fields. Surely would have >>>>> eliminated much verifier complexity.) >>>>> >>>> accessing to the identity hashcode or the current class inside a >>>> constructor is valid (i believe) but those are a corner cases. >>>> >>> >>> Ah, yes. This generalizes to calling methods that safely operate on an >>> already-initialized superclass (typically instance methods of the >>> superclass). >>> >>> If we someday have abstract records or other forms of user-defined >>> superclasses, it will be quite reasonable to call the superclass's instance >>> methods from the subclass's constructor. >>> >> >> So maybe `super` is DA but `this` is DU, just like in the code >> before the super-constructor call. (I’m abusing the terms DA/DU >> like Brian is, and you call out, but they are close to correct.) > > I think this means I can't call inherited method 'getParentWidget()' or some > static utility 'computeWidgetOfParent(this)' method (e.g., > 'identityHashCode(this)'). I *can* call 'super.getParentWidget()'. > > It's a do-able way to apply some discipline. Feels a little heavy on the "you > can't do that" side and light on the "we'll guarantee better programs" > side—because of course, once you've called the super method, it can do > whatever it wants with the object. > > Overall, my sense is that controlling all accesses of 'this' (explicit and > implicit) is more ambitious than we really want/need here. Airtight > constructors are a problem for another day. Prohibiting assignment to the > instance fields is more manageable.
I’m obviously not proposing airtight constructors—although you get that as a forced move (and probably a pleasant one, to boot), for free, whenever you choose to use inline classes. Let's keep the existing problems with constructors as they are: You can call a super method, which via an override can “see” an incomplete instance. This means that if we forbid “this” in record default constructors, if there is a sneaky way to get “super”, then the usual sneaky things can happen. In fact, if we forbid “this.x = y” (only) then the same sneaky things can happen. The question is see right now is whether forbidding “this” or forbidding “this.x = y” is simpler. I think the former is simpler. The latter is less restrictive, but more complex. Which leads to a better user experience? The simpler, as long as the extra restriction does not require the user to resort to complex workarounds. My observations about “super” are a red herring, I guess; I’m just reaching for an escape hatch away from the proposed restrictions about “this”. (I just noticed that “super” is DU before the “super” call, so it’s not as useful as I thought. I don’t want to entangle the present discussion with lame proposals for extending the usefulness of the “super” keyword.) — John