Why does this() and super() have to be the first statement in a constructor?

Joseph Darcy joe.darcy at oracle.com
Fri Oct 28 17:31:39 PDT 2011


Hello,

I have no plans to work on fleshing out a proposal in this problem space.

My assessment of the problem is that it is certainly an irritation, but 
that the opportunity cost of fixing this irritation as opposed to making 
other language improvements is not favorable.

Even given a formal proposal and an implementation, there would be a 
nontrivial testing cost.

-Joe

On 10/16/2011 4:41 PM, Howard Lovatt wrote:
> I proposed this a long while ago, see email chain below. My particular 
> requirement was wanting a field initialised so that the super 
> constructor could call an instance method defined in 
> the derived class. The example I gave in the email below was contrived 
> to keep it short. The actual use case was very similar to an inner 
> class (therefore easy to see why you would want this because inner 
> clas do this already).
>
> My proposal was to allow read and write of a class's own fields (not 
> those in super) and local variables before super/this was called.
>
> Would the above description be a sufficiently detailed request to 
> start working on a formal proposal? Is this something that is likely 
> to get support if a formal proposal was submitted?
>
> Cheers,
>
>  -- Howard.
>
> =================================================================
>
> from 	IncidentDaemon at sun.com <mailto:IncidentDaemon at sun.com> 
> IncidentDaemon at sun.com <mailto:IncidentDaemon at sun.com>
> to 	howard.lovatt at iee.org <mailto:howard.lovatt at iee.org>
> date 	23 February 2006 21:37
> subject 	Your Report (Review ID: 654094) - Alow field inizialization 
> before super call in constructors
>
> 	
> hide details 23/02/2006
> 	
>
> ************************************************
> Your report has been assigned an internal review ID of: 654094
>
> This review ID is NOT visible on on Sun Developer Network (SDN).
>
> We greatly appreciate your interest in improving the quality of 
> Java(tm) Technology from Sun Microsystems.
>
> Please be aware that the large volume of reports we receive sometimes 
> prevents us from responding individually to each message.
>
> We currently have a three week average response time.  If the 
> information is determined to be a new bug, or a duplicate of a known 
> bug, you will receive a followup email containing a seven digit bug 
> number.  You may search for, view, or vote for this bug on the Bug 
> Database at http://bugs.sun.com/
> .
>
> If you just reported an issue that could have a major impact on your 
> project and you require a timely response, please consider purchasing 
> one of the support offerings at http://java.sun.com/support/index.html
> .
>
> The Sun Developer Network (http://developers.sun.com 
> <http://developers.sun.com/>
> ) is a free service that Sun offers.  To join, visit 
> http://developers.sun.com/global/join_sdn.html
> .
>
> For a limited time, SDN members can obtain fully licensed Java IDEs 
> for web and enterprise development.  More information is at 
> http://developers.sun.com/prodtech/javatools/free/
> .
>
> Thank you for your help.
>
>
>
> ---------------------------------------------------------------
>
>
> dateCreated: Thu Feb 23 03:37:04 MST 2006
> type: rfe
> cust_name:   Howard Lovatt
> cust_email: howard.lovatt at iee.org <mailto:howard.lovatt at iee.org>
> jdcid:       hlovatt
> status:      Waiting
> category:    java
> subcategory: specification
> company:     Personal submission
> release:     5.0
> hardware:    x86
> OSversion:   win_xp
> priority:    4
> synopsis:    Alow field inizialization before super call in constructors
> description: A DESCRIPTION OF THE REQUEST :
> At present some code cannot be written using Java source code you need 
> to manipulate the bytecode. In particular the Java language requires 
> that super be the first line of a constructor. However there are times 
> when you need to initialize a field from arguments supplied to the 
> constructor before calling the constructor. So that the 
> super constructor can call virtual methods defined in the base class 
> and not get errors (e.g. NullPointerException). EG:
>
> class Base {
>    Base() { System.out.println( get_int() ); }
>    abstract int get_int();
> }
>
> public class Derived extends Base {
>    Integer value;
>    Derived ( int value ) { this.value = value; } // NB Autoboxed
>    int get_int() { return value; } // NB unboxed automatically
>
>    public static void main( String[] notUsed ) { new Derived( 1 ); } 
> // NullPointerException!
> }
>
> The above code throws a null pointer because you can't initialize 
> field value before calling super (implicitly) in Derived's constructor.
>
> The suggested solution is to allow super to appear after the 
> initialization, e.g. allow:
>
> Derived( int value ) {
>    this.value = value;
> super()
> }
>
> If super isn't explicityly mentioned then, as at present, it is 
> assumed to be the first line.
>
> JUSTIFICATION :
> There are plenty of examples were initializing fields is needed.
>
> EG1 you can't manually write the equivalent of an inner class because 
> the field that points to the outer class needs to be initialized 
> before the call to super.
>
> EG2 this problem has been recognized for C# and an MS proposed 
> language extension called 
> SPEC#(http://research.microsoft.com/projects/specsharp/papers/krml136.pdf
>  on page 3) is to adopt C++ style field initialization after the : 
> following the constructor name and before the base (super) call. EG 
> the example above in SPEC# would be:
>
> Derived( int value ) : this.value( value ), base() {}
>
>
> CUSTOMER SUBMITTED WORKAROUND :
> The only work around I know is to manipulate the bytecode. The system 
> I have used is to pass normal Java through the compiler (with 
> super before field initialization) and then use a bytcode manipulator 
> called Javassist to move the call to super to after the field 
> initialization as a post processing operation on the class file.
> workaround:
> comments:    (company - Personal submission , email - 
> howard.lovatt at iee.org <mailto:howard.lovatt at iee.org>)
> =================================================================
>
> On 9 October 2011 13:42, Joe Darcy <joe.darcy at oracle.com 
> <mailto:joe.darcy at oracle.com>> wrote:
>
>     Ulf Zibis wrote:
>     > Anyway,
>     >      int c = a + b;
>     > doesn't affect any object field initialization.
>     > It's just a local variable, which gets lost after the instance
>     is instantiated.
>     >
>     > As workaround, you can always use a static helper method which
>     does the same:
>     >      super(staticHelper(a, b));
>     >
>     > So I agree, it would reasonable, to allow some code in advance
>     of this() or super().
>     >
>     > + 1 for your proposal, Vimil Saju.
>     >
>
>     This is not a proposal, it is a question!
>
>     The answer to the question has already been given on the list: since
>     superclass state of the object is not initialized until after the
>     superclass constructor is called, the Java language requires that
>     a call
>     to a superclass constructor occur in the first statement of a subclass
>     constructor in an attempt to reduce logic errors in initialization.
>
>     This restriction is annoying at time, but no one has put forward a
>     detailed proposal for how the requirement could be sensibility
>     loosened
>     in a way that can be standardized and tested.
>
>     -Joe
>
>     > -Ulf
>     >
>     >
>     >
>     > Am 08.10.2011 01:39, schrieb Daniel Yokomizo:
>     >
>     >> On Oct 7, 2011 1:58 PM, "Paul Benedict"<pbenedict at apache.org
>     <mailto:pbenedict at apache.org>>  wrote:
>     >>
>     >>> It's a compiler error because the superclass is guaranteed to be
>     >>> initialized first before the subclass.
>     >>>
>     >> Not guaranteed by the JVM, as in anonymous inner classes.
>     >>
>     >>
>     >>> On Fri, Oct 7, 2011 at 11:51 AM, Vimil
>     Saju<vimilsaju at yahoo.com <mailto:vimilsaju at yahoo.com>>  wrote:
>     >>>
>     >>>> If you have subclass then java requires that this() or super
>     has to be
>     >>>>
>     >> first statement in the constructor of the subclass.
>     >>
>     >>>> Here is an example
>     >>>>
>     >>>> publicclassMyClass{
>     >>>>          publicMyClass(intx){}
>     >>>> }
>     >>>>
>     >>>> publicclassMySubClassextendsMyClass{
>     >>>>          publicMySubClass(inta,intb){
>     >>>>                  intc =a +b;
>     >>>>                  super(c); // COMPILE ERROR
>     >>>>          }
>     >>>> }The above compilation error can be resolved by rewriting the
>     code in
>     >>>>
>     >> the constructor as follows
>     >>
>     >>>> publicclassMySubClassextendsMyClass{
>     >>>>          publicMySubClass(inta,intb){
>     >>>>                  super(a + b);
>     >>>>          }
>     >>>> }Can't the Java compiler detect that in the previous code
>     there was no
>     >>>>
>     >> access to the instance fields or methods and therefore allow
>     the code to
>     >> compile without any error.
>     >>
>     >
>     >
>
>
>
>
>
> -- 
>   -- Howard.
>



More information about the coin-dev mailing list