JNI.h中_jobject等空类与JVM内部Object类的关系及空类原因问询
_jobject Great question—these empty classes in jni.h are a clever, purpose-built part of how JNI bridges Java and native C/C++ code, and they make a lot more sense once you break down their role.
Let’s break this down step by step:
1. These are type markers, not actual implementation classes
The empty classes like _jobject, _jclass, and _jstring don’t have any fields or methods because they don’t need to. In native code, you never create instances of these classes directly—instead, you work with pointers to them (for example, jobject is just a typedef for _jobject*).
These classes exist solely for compile-time type safety. They let the C/C++ compiler enforce that you’re using the right kind of Java object pointer in the right place. For example, you can’t accidentally pass a _jstring* to a function expecting a _jintArray* without an explicit cast, which helps catch bugs early in the development process.
2. _jobject and the JVM’s internal Object class: A logical mirror, not a direct link
_jobject is the root of the JNI type hierarchy, directly mirroring java.lang.Object as the root of Java’s type system. Here’s how they connect:
- In Java, every class inherits from
Object; in JNI, every native object type (like_jclass,_jstring,_jarray) inherits from_jobject. - The JVM’s internal
Objectimplementation (in files likeObject.h/Object.cpp) is the actual data structure that holds a Java object’s state. Native code never accesses this structure directly—instead, the_jobject*pointer you get in native code is a handle that the JVM maps to its internalObjectinstance behind the scenes.
Think of _jobject as a "type label" your native code uses to say, "This pointer refers to some Java object," while the JVM handles all the actual object storage and logic under the hood.
3. The inheritance hierarchy mirrors Java’s type system exactly
The chain like _jarray : public _jobject, _jintArray : public _jarray is a direct mirror of Java’s own type hierarchy:
_jarraycorresponds to Java’sjava.lang.reflect.Array_jintArraycorresponds to Java’sint[]- And so on for all primitive array types and
Object[]
This mirroring lets native code follow Java’s type rules naturally. For example, just like you can cast a String to Object in Java, you can safely cast a _jstring* to _jobject* in native code.
Why empty classes work so well
JNI is designed to keep native code decoupled from the JVM’s internal implementation details. By using empty marker classes:
- The JVM can change its internal
Objectstructure (for performance or feature updates) without breaking existing native code (as long as the pointer handles still map correctly). - Native code doesn’t need to know anything about how the JVM stores Java objects—all interactions happen through safe, standardized JNI functions like
GetObjectClass,GetStringUTFChars, orSetIntArrayRegion.
内容的提问来源于stack exchange,提问作者LeAdErQ

