0

Possible Duplicate:
Interview : Can we instantiate abstract class?

I have an abstract class with all its methods defined (i.e. there are no abstract methods contained within it) like the following:

public abstract class MyAbstractClass {
  String s;
  public void setString(String s) {
    this.s = s;
  }
  public String getString() {
    return this.s;
  }
}

There is also a JUnit test class:

public class TestClass {

  MyAbstractClass c;
  @Before
  public void setUp() {
    // What is happening here? And why does this work with an abstract class?
    // Instantiation? Extending the abstract class? Overwriting?
    c = new MyAbstractClass() { };
    // This will not work: (Why?)
    // c = new MyAbstractClass();
  }

  @Test
  public void test_AllMethodsAvailable() {
    // Why can I access the abstract class' methods?
    // Shouldn't they be overwritten? Or did I extend the class?
    c.setString("Test");
    assertEquals("Test", c.getString());
  }
}

I don't quite understand why the assignment to c works in the first case but not in the second, or what is actually happening there (and as a consequence, why accessing the abstract class' methods works in the test).

Can somebody please explain (and possibly point me to a Javadoc, article or book that explains why this works)?

Why can I "instantiate" an abstract class there? (Is that actually what I'm doing?)

Has it to do with inner classes?

Community
  • 1
  • 1
Christian
  • 6,070
  • 11
  • 53
  • 103

4 Answers4

2

You are creating an anonymous inner class with that code. The class you create this way is implicitly extending MyAbstractClass.

Since your abstract class does not have abstract methods you don't have to provide implementations so this works.

If you don't know about inner classes you can check the official documentation which is quite nice I think.

Adam Arold
  • 29,285
  • 22
  • 112
  • 207
  • Thanks. Though I think the "overwrite" tag was useful in that others who are new to Java might search for that word if they have a similar problem. I know I did... :) – Christian Jan 28 '13 at 12:52
1

Has it to do with inner classes?

 c = new MyAbstractClass() { };

Absolutely, the above is anonymous inner class declaration, you are not really instantiating an abstract class(which you can't) here but you are actually creating an Anonymous inner class(a sub-type of MyAbstractClass)

PermGenError
  • 45,977
  • 8
  • 87
  • 106
0

When you write c = new MyAbstractClass() { };, you actually create an anonymous class which extends MyAbstractClass, and which is not abstract. Since MyAbstractClass already has all method defined, the instanciation is valid.

Bastien Jansen
  • 8,756
  • 2
  • 35
  • 53
0

Your assignment to c works because you are subclassing MyAbstractClass with an anonymous non-abstract class, the c is an instance of the non-abstract class.

Since you don't have any abstract methods in your abstract class, your anonymous class doesn't have to implement anything.

NickJ
  • 9,380
  • 9
  • 51
  • 74