简体   繁体   中英

Will Java record classes be allocated on the stack?

public class Hello {
  public static void main(String[] args) throws Exception {
    System.out.println(ProcessHandle.current().pid());
    var p = new Poing(1,2);
    Thread.currentThread().join();
  }
}
record Point(int x, int y) {}

If I new a Point object, will this object be allocated on the stack?

JDK version java version "18.0.2" Java HotSpot(TM) 64-Bit
JVM args java -Xcomp -XX:-UseCompressedOops -XX:-UseCompressedClassPointers Hello.java
I use jhsdb to see if the point object is still allocated in the heap. So I have a question, will simple objects be allocated on the stack?

Pulling together the various comments into an answer...

Will Java record classes be allocated on the stack?

In general: No. Java record classes are first class. They have reference-based identity and record values are not limited by the language to the scope in which they were allocated. Therefore, in general they cannot be allocated on the stack.

The JIT compiler in a current generation HotSpot JVM can perform a form of optimization called escape analysis ... to determine if objects allocated in a method are able to "escape". This involves analysis of the method that allocated the object and any other methods that it passes the object to. If an object can be shown to never escape, the JIT compiler can arrange that it is not allocated in the heap. For more details see:

Note that escape analysis applies to record classes and other (regular) Java classes. It depends on how the objects are used, and whether the JIT compiler can establish the preconditions exist. Things that could inhibit the optimization include:

  • assigning the record object reference to the field of some other object or array
  • returning the record object from the method that created it,
  • debugging the JVM.

Note that escape analysis only happens when the method that allocates the record object is JIT compiled. In your example, the main method code will not be run enough times to trigger JIT compilation.


@Jesper mentions Value Objects as proposed by this draft JEP . This is a new kind of class for which would have value-based identity semantics. The == operator would compare them by comparing the objects' fields rather than their references. These could be optimized to allocate the values on the stack or to embed them in other objects; eg on the heap.

So Value Objects would be a good way to get (probably) stack-allocated objects.

However:

  • This is just a draft proposal. It doesn't have JEP status yet.
  • A JVM could just allocate value objects as normal objects. Indeed the proposal still describes value classes as reference types.
  • Java record classes are not value classes anyway. In the proposal, a value class is flagged with the keyword value , and this may be applied to record classes. It is NOT proposed to retrospectively make all record classes value classes: that would be a breaking change.

@dan1st mentions Primitive Classes as described in JEP 401 . These differ from Value Objects in that the are NOT reference types at all. That means that they cannot be compared with null . However there will be conversions to translate between (corresponding) Primitive class and Value class objects.


It should be noted that these features are not yet present in or (publicly) scheduled for any upcoming mainstream Java release. And they could change in the meantime.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM