What does Java look like in memory

I am new to java and still learning. I hugged inner and anonymous classes. Now I have a technical question about how Java looks in memory when distributing objects, defining classes, etc.

Like what it looks like in memory when I have a field that is an object that is defined in an outer class and inner class. Do static classes look different than non-static?

I just need a visual link.

Thanks guys

+7
java memory
source share
6 answers
+4
source share

Details are given in the implementation (and not in the specification). However, implementations usually follow a very simple pattern. Most of the memory layout in Java is very simple and straightforward. My terminology may not correspond to the Java terminology, since I do not deal with a lot of Java programming.

In general, an object starts with a pointer to its vtable, and then has a bunch of fields that follow. Fields are either primitive types (int / bool / float) or pointers to objects. What is this for objects. (Classes are also objects.) Null pointers are like C, they are not valid, not like Python, where None is an object.

The inner class has an additional hidden field that points to an instance of the outer class. In this way, inner classes access data in the outer class. Anonymous classes work the same way. Static methods are just class methods, not instance methods.

The vtable has all the magic. Each class has its own virtual table, shared between all objects. Vtable has information about the class, such as the size of its instances and how fields are laid out. This information is used by the garbage collector. The vtable also has pointers to all the methods that the class implements. When you call a method, the runtime first grabs the vtable pointer from the object, then it grabs the method pointer from the vtable, then it calls the method and passes the object to the method as an implicit parameter. It is similar to C ++, but much easier to implement. A process may be skipped if the method or class is "final".

I know that Java really does not have “pointers”, it has “symbolic pens” or something like that, but common implementations just use plain old pointers.

+3
source share

Welcome to the Java world. Unlike the C language, where building the language and representing the memory are pretty much related to each other, Java is a bit more complicated.

First of all, when people talk about Java, this can mean two things: the Java language and the Java platform. Here I will call Java the Java programming language. Code written in Java is first compiled into bytecode, machine code for the Java virtual machine. If you are interested in the details of the Java language, here is the Java language specification . And for the JVM, the Java Virtual Machine Specification .

what memory looks like when I have a field that is an object that is defined in an outer class and inner class.

I interpret this as the memory layout in the Java virtual machine looks like, since the physical layout is consistent with the JVM implementation. To do this, I removed the Java Virtual Machine Structure .

Like the Java language, the Java virtual machine works with two types of types: primitive types and reference types. There are, respectively, two types of values ​​that can be stored in variables, passed as arguments, returned by methods, and work with: primitive values ​​and reference values.

The Java virtual machine expects that almost all type checking is performed at compile time, and not the Java virtual machine itself. In particular, data does not have to be tagged or otherwise verified to determine types.

....

An object reference is considered to be a Java reference virtual machine type. Values ​​of type reference can be considered as pointers to objects.

So the answer seems to be that both fields will look the same: reference .

+3
source share

How and what memory looks like when I have a field that is an object that is defined in an outer class vs inner class. Static classes look different than non-static?

An instance of a non-static inner (or anonymous) class will refer to an instance of the outer class that was used to create it. This is what allows a method in the inner class to refer to instance level members declared in the enclosing class. Typically, this reference is passed to the inner class as a hidden optional parameter in the constructor. But if you use reflection to create an internal instance of the class, you must explicitly specify this optional parameter.

(Note that another mechanism is used when an anonymous class uses locales / parameters in the scope of the method that creates it ...)

If you need more detailed information, you can use javap to disassemble the bytecodes of some simple example classes.

I just need a visual link.

Sorry, I do not take nice photos :-)

+1
source share

A static (nested) class works just like a top-level class. The only difference is that its name has a different class name, prefix. (If you look at the compiled .class files, you will see that you get something like "Outer $ Nested.class" for a class called Nested, nested in a class called Outer.)

The inner class has a hidden field that is a reference to the containing instance of its outer class. When you write:

 class Outer { final int x; class Nested { int y; Nested(int y) { this.y = y; } int bar() { return x + y; } } void foo() { Nested n = new Nested(5); } } 

It is as if you wrote:

 class Outer { final int x; static class Nested { Outer outer; int y; Nested(Outer outer, int y) { this.outer = outer; this.y = y; } int bar() { return outer.x + y; } } void foo() { Nested n = new Nested(this, 5); } } 

The name of this hidden field (which I call "external" here) is hidden to you, although you can refer to it by saying Outer.this inside the inner class (where Outer is the name of your outer class, of course). Also note that when a method in an inner class refers to something in an outer class, that reference is actually related to that hidden reference to the outer class.

There are a few additional complications as to how access control (for example: private) works with nested / inner classes, but this does not affect the "memory" question you ask.

0
source share
 public class I { class inner { public void ctor() {}; } } 

Looks dissasemmbled like you could use jad

 class I$inner { // Field descriptor #6 LI; final synthetic I this$0; // Method descriptor #8 (LI;)V // Stack: 2, Locals: 2 I$inner(I arg0); 0 aload_0 [this] 1 aload_1 2 putfield I$inner.this$0 : I [10] 5 aload_0 [this] 6 invokespecial java.lang.Object() [12] 9 return Line numbers: [pc: 0, line: 3] Local variable table: [pc: 0, pc: 10] local: this index: 0 type: I.inner // Method descriptor #14 ()V // Stack: 0, Locals: 1 public void ctor(); 0 return Line numbers: [pc: 0, line: 4] Local variable table: [pc: 0, pc: 1] local: this index: 0 type: I.inner } 

Like hexdump, it will start with 0xcafebabe

0
source share

All Articles