Lifting the restriction on the number of public classes per file

Brian Goetz brian.goetz at oracle.com
Tue Nov 27 17:47:25 UTC 2018


When we have sealed classes and records, it will be practical and 
sensible to declare entire related hierarchies together:

-- Shape.java
     sealed interface Shape { }

     record Circle(Point center, int radius) extends Shape;
     record Square(Point corner, int length) extends Shape;
--

Not only is it inconvenient for the writer to require each get their own 
source file, but more importantly, it is bad for the reader -- 
separating these declarations makes it hard to see what is a group of 
related entities.  (Imagine if we required a separate source file for 
each enum constant; it would be much harder to see the structure of an 
enum.)  So we want to encourage this sort of co-declaration.

It is an easy rejoinder to say "Then just declare them as nested in the 
Shape, and use static imports to clean up the use-site damage from 
that."  But this is a bad answer, because, as Remi and Maurizio point 
out, this affects _the structure of your public API_.  But that means 
we're putting users in a place where they get to pick two of the 
following three features:

  - Use sealing
  - Declare a sealed hierarchy with its source together
  - Declare a flat API

I've seen API style guides that forbid the use of public nested 
classes.  And while I don't personally program this way, I think its a 
not-ridiculous house style.  But then people in this situation have to 
write in a less readable, less maintainable way.

So, my "for whatever reason" means: People should get to choose the 
shape of their exported APIs (and flat is a valid shape preference), and 
not be forced into a particular shape because they want to use sealing.  
The API shape above -- a sum of records -- is one we should encourage, 
not discourage.



On 11/26/2018 2:43 PM, Kevin Bourrillion wrote:
> Sorry for delay. Can we unpack the "for whatever reason" part?  For 
> what reason?
>
> Unsurprisingly to anyone, we actually hard-ban this practice here. 
> Multiple top-level classes per file just make code harder to find; 
> what are the advantages?
>
> On Mon, Nov 12, 2018 at 8:35 AM Brian Goetz <brian.goetz at oracle.com 
> <mailto:brian.goetz at oracle.com>> wrote:
>
>     This was received through amber-spec-comments.
>
>     I agree with the general sentiment, especially for sealed types,
>     where we want to define an entire sealed type hierarchy in a
>     single compilation unit (but for whatever reason, prefer not to
>     nest the subtypes in the super type.)  There are some details to
>     be worked out (e.g., use of the SourceFile attribute by tools).
>
>>     Begin forwarded message:
>>
>>     *From: *Francois Green <francois.green at gmail.com
>>     <mailto:francois.green at gmail.com>>
>>     *Subject: **Lifting the restriction on the number of public
>>     classes per file*
>>     *Date: *November 11, 2018 at 10:09:06 PM GMT+1
>>     *To: *amber-spec-comments at openjdk.java.net
>>     <mailto:amber-spec-comments at openjdk.java.net>
>>
>>     In the face of the changes in code style that records will bring
>>     about, has
>>     there been renewed discussion about lifting the restriction?
>>
>>        public interface Blue;
>>        public record IKB() implements Blue;
>>        public record Azure() implements Blue;
>>        public record Royal() implements Blue;
>>
>>     Having to place each line in the code above in its own file seems
>>     harsh.
>
>
>
> -- 
> Kevin Bourrillion | Java Librarian | Google, Inc. |kevinb at google.com 
> <mailto:kevinb at google.com>

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.openjdk.java.net/pipermail/amber-spec-experts/attachments/20181127/58c0eabc/attachment.html>


More information about the amber-spec-experts mailing list