Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Difference between Interface and Class object memory allocation

Suppose there are Interface A and class B, and class B implements the interface;

interface A {
  void hello();
}

class B implements A {
  public int justAField;

  @Override
  public void hello() {
    System.out.println("Hi.");
  }

  public void anotherMethod() {
    System.out.println("Another one.");
  }
}

And let's say, we have these two objects;

A typeInterface = new B();
B typeClass = new B();

My question is, when compiler compiles the code and when the memory allocation begins, we've got two objects right? But one is type A, one is type B, that means 'typeInterface' will have only one method, but 'typeClass' will contain one more field and one more method.

Does these two objects allocate the same amount of memory or 'typeInterface' basically consume much less memory?

like image 573
ilkerrilker Avatar asked Dec 23 '22 15:12

ilkerrilker


2 Answers

No, you have two objects of type B, one stored on a reference of type A, the other one stored on a reference of type B.

Both objects share the same memory usage size, but you cannot access the methods of B from the reference of type A (the reference named typeInterface), even if the method exists at the referenced object, unless you cast it. If you cast the reference, then the restriction is removed and you can access anotherMethod.

You must differentiate between references and objects. That's all you need.

like image 103
Victor Polo De Gyves Montero Avatar answered Feb 15 '23 23:02

Victor Polo De Gyves Montero


My question is, when compiler compiles the code and when the memory allocation begins, we've got two objects right?

Yes.

But one is type A, one is type B, ...

No!!

Both are type B. The expression new B(...) creates a B. What happens after that doesn't change that.

In the first example, you are then assigning the reference for a B instance to a variable whose type is A. That means that you will only be able to use A features (methods, fields) when you access the object via that variable.

However, the object itself is still an instance of B, and will remain that way for the lifetime of the object. And we can prove it1.

  System.out.println(typeInterface.getClass().getName());

will print "B", not "A".

And we can go a step further by casting typeInterface to a B and using the B methods and fields ... to show that it is really a B.

It is a B. Unequivocally.

... that means 'typeInterface' will have only one method, but 'typeClass' will contain one more field and one more method.

No. Not true. This logic is based on a false assumption. See above.

Does these two objects allocate the same amount of memory or 'typeInterface' basically consume much less memory?

Yes they user the same amount of memory. They are both B instances. See above.


One way to understand this is that when you do the assignment in this:

A typeInterface = new B();

the compiler "forgets" about the B-ness of the object that typeInterface (now) refers to. It only "remembers" that it refers to an A of some kind. However, at runtime, the runtime system always knows what an object's real type is, so that it can correctly implement instanceof, type-casts, getClass(), method dispatching and so on.


1 - The javadoc for Object::getClass() states: "Returns the runtime class of this Object".

like image 30
Stephen C Avatar answered Feb 16 '23 00:02

Stephen C