Classes, specializations, and statics

Brian Goetz brian.goetz at oracle.com
Fri Feb 19 00:54:53 UTC 2016


> Based on the example above, I think we need to be more explicit about 
> how the <clinit> method is handled.
> There are really two different sets of statics that need to be handled 
> by the class initialization:
> A) common statics (shared across all instantiations)
> B) specialized statics
> In addition to the statics, there is also common (and maybe 
> specialized?) code that is run as part of <clinit>.

There is a reasonable model to collapse these back into one concept; 
treat "common statics" as specialized statics on the all-erased 
parameterization, with a <where> clause that restricts them to that 
parameterization.  Not clear whether we actually want to represent it 
that way or not, but its a useful mental model that doesn't require the 
creation of a third thing.  (Since Class[Foo] and ParamType[Foo,erased*] 
describe the same class, this is also fully binary compatible with 
existing classes.)

Which means we can do a similar thing with <clinit>, if we want.  I'll 
wave my hands because we've not yet talked much about conditional 
members, but it basically looks like this:

<where T*=erased*>
<init>() { /* common static init code */
                /* specializable init code */ }

<init>() { /* specializable init code */ }

Or not.

> Where will the initialization code for both kinds of statics be?  The 
> existing <clinit> method?

We have two choices:
  - have a new <sclinit> block that gets run once per specialization, 
and keep <clinit>
  - merge the two as above, exploiting planned support for conditional 
members

Either way, as you say, we have to ensure that the common init runs 
exactly once.
> When using *static, are we only discussing {get,put}?  Or is this also 
> proposing invokestatic changes to allow specialized static methods?

Methods too.

> All of the technical details aside, is this something we really want 
> to expose to the users?  They're going to have a hard time 
> understanding why Foo<int> (or Foo<ValueType) gets specialized statics 
> while Foo<String> & Foo<Bar> share the erased version.

I think this is mostly a matter of coming up with the right syntax, 
which makes it clear that statics can be per-class or 
per-specialization.  There are a whole pile of related 
specialization-related syntax issues, I'll try to get them all in one 
place.




More information about the valhalla-spec-observers mailing list