Draft JLS spec for records

forax at univ-mlv.fr forax at univ-mlv.fr
Thu Sep 5 13:15:35 UTC 2019

----- Mail original -----
> De: "John Rose" <john.r.rose at oracle.com>
> À: "Remi Forax" <forax at univ-mlv.fr>
> Cc: "Gavin Bierman" <gavin.bierman at oracle.com>, "amber-spec-experts" <amber-spec-experts at openjdk.java.net>
> Envoyé: Jeudi 5 Septembre 2019 01:27:23
> Objet: Re: Draft JLS spec for records

> On Sep 3, 2019, at 5:02 AM, forax at univ-mlv.fr wrote:
>> Given that i've always find the syntax of the canonical constructor too close to
>> the one of the real constructor (depending on the fact that parenthesis are
>> present or not),
>> i propose a new kind of initializer, the require initializer (obvisouly it can
>> be another name than "require").
>> An example of syntax:
>>   record Foo(String s) {
>>     require {
>>       Objects.requireNonNull(s);
>>     }
>>   }
>> I also believe we should make the instance initializer illegal in record given
>> that a require initializer is a kind a better instance initializer because it
>> can access local variables.
> The reason those initializers cannot “see” constructor parameters is (as you
> noted later) the initializers are incorporated into every constructor, and thus
> cannot assume any particular set of parameter names.
> OTOH, if you are incorporating only into the canonical constructor of a record,
> you *can* assume all component names are in scope.
> In fact, OTOOH, in some sense *every* constructor of a record has *all*
> component names in scope, so the initializer of a record *could* have those
> names.  It doesn’t even have to be a new kind of initializer, just a new power
> of the existing initializer in the restricted context of a record, where all
> components are always in scope.
> So (a) don’t add the keyword and (b) all instance initializers to access full
> context of a record’s components.  Brian will immediately say that this makes a
> questionable syntax choice (yes, I plead guilty to that) into an attractive
> nuisance, so that’s a reason to maybe require a keyword to opt into the nice
> new features of IIs.
> OTO^3H, since the canonical constructor is central to a record in a special way,
> it makes perfect sense to (1) put all the juicy validation/normalization logic
> into the body of the main constructor, and (2) look for ways to slim down the
> syntax of that constructor so, in common cases, it looks as slim and friendly
> as an instance initializer.  So:
>  record Foo(String s) {
>    constructor {
>      Objects.requireNonNull(s);
>    }
>  }

it looks like JavaScript, are you, even subconsciously, trying to bridge the gap between Java and JavaScript :)  

> But that’s so close to the proposed CompactConstructorDeclaration syntax that we
> are now arguing about matters of taste.

given that we have determine that it really works more as a simplified constructor than a block/initializer, i believe the compact constructor syntax is fine.

> My taste-meter doesn’t budge for the missing parentheses of “Foo { }”, but the
> needle *does* twitch a little because of the obligation to say “public” before
> every compact constructor declaration.  Surely that’s not necessary.  Since
> interfaces *also* require certain members to be public, *and* they allow
> “public” to be elided, it seems like records should provide the same courtesy.
> I’m sure that’s already been discussed, but I’ll add my vote for eliding
> “public” at that point.

can someone explain me why we need the constructor to be public ?

> — John


More information about the amber-spec-observers mailing list