1

I have an abstract superclass that has a protected String variable. It is not initialized in the superclass.

All I want to do is initialize and use it in a subclass. So, I have something like this:

    public class MySubclass extends MyAbstractSuperclass {        
        thing = "i'm a thing";
        [...]
    }

Seems simple enough, since the whole point of inheritance is reusing classes and their fields in different contexts. But that is wrong: Syntax error on token "thing", VariableDeclaratorId expected after this token.

I can get it to compile by putting brackets around the subclass initialization. What I would like to know is why the first way is wrong, and why brackets fix it. Thanks for any help.

edit: I appreciate the tip that I can fix this by using a constructor. However, I am still curious as to what is actually wrong with using a superclass field in this way, as it seems to me to be pretty intuitive. And also, why do the braces fix it, what exactly does it mean to surround a statement with braces like that outside of e.g. a loop structure?

aearon
  • 393
  • 4
  • 9
  • 1
    The braces are creating an [instance initializer](http://stackoverflow.com/questions/6763550/why-java-instance-initializers) – GriffeyDog Feb 04 '13 at 20:48

3 Answers3

3

This is not Scala, you must write an explicit constructor:

public class MySubclass extends MyAbstractSuperclass {        
    public MySubclass() {
        thing = "i'm a thing";
        [...]
    }
}

or use a constructor with parameter:

public abstract class MyAbstractSuperclass {

    protected final String thing;

    protected MyAbstractSuperclass(String thing) {
        this.thing = thing;
    }

}

public class MySubclass extends MyAbstractSuperclass {
    public MySubclass() {
        super("i'm a thing");
    }
}
Tomasz Nurkiewicz
  • 334,321
  • 69
  • 703
  • 674
  • Well, I could do that. But it does compile if I put the braces around it, why is that? I understand why a constructor works. But I'd never seen the braces around a statement like that without reference to anything like a if type keyword. – aearon Feb 04 '13 at 20:41
  • 1
    @aearon see: http://stackoverflow.com/questions/2007666 and http://stackoverflow.com/questions/1958636 – Tomasz Nurkiewicz Feb 04 '13 at 20:57
1

What I would like to know is why the first way is wrong, and why brackets fix it. Thanks for any help.

public class MySubclass extends MyAbstractSuperclass {        
    thing = "i'm a thing";
    [...]
}

You try to do a statement here, set the value of the variable thing to text. You can not do statements here, you can only do variable declaration here.

public class MySubclass extends MyAbstractSuperclass { 
    {       
        thing = "i'm a thing";
    }
    [...]
}

Now, you have a initializer block, this one is executed as a statement (before the constructor). Therefore, you can access thing, because visibility is protected. See for example here: http://docs.oracle.com/javase/tutorial/java/javaOO/initial.html

tb-
  • 1,240
  • 7
  • 10
0
public class MySubclass extends MyAbstractSuperclass {        

        public MySubclass(){
         super.thing= "i'm a thing";
         }
    }
Gabriele Mariotti
  • 320,139
  • 94
  • 887
  • 841