In addition to Weibo, there is also WeChat
Please pay attention
WeChat public account
Shulou
2025-03-04 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >
Share
Shulou(Shulou.com)06/02 Report--
This article mainly explains "how to use the hashCode method of java Object". The content of the explanation is simple and clear, and it is easy to learn and understand. Please follow the editor's train of thought to study and learn "how to use the hashCode method of java Object".
1. Background introduction
When overriding the hashCode method, I was curious to see that the data printed out by hashCode looked like an address value.
In addition, recently I have been studying the jvm source code, so I would like to find out how hashCode is implemented in hotspot.
two。 Call the procedure to comb the Object code public native int hashCode () of java
Through the official jdk Object.class source code, it is found that hashCode is modified by native. Therefore, this method should be implemented in jvm through cCandle +.
HashCode related code of jvm
First, look at the Object.c code corresponding to Object.java.
/ / File path: jdk\ src\ share\ native\ java\ lang\ Object.cstatic JNINativeMethod methods [] = {{"hashCode", "() I", (void *) & JVM_IHashCode}, / / this method is the hashCode method we want to see {"wait", "(J) V", (void *) & JVM_MonitorWait}, {"notify" "() V", (void *) & JVM_MonitorNotify}, {"notifyAll", "() V", (void *) & JVM_MonitorNotifyAll}, {"clone", "() Ljava/lang/Object ", (void *) & JVM_Clone},}
Go further into the jvm.h file, which contains many interfaces for java to call the native method
/ / hotspot\ src\ share\ vm\ prims\ jvm.h/* * java.lang.Object * / JNIEXPORT jint JNICALLJVM_IHashCode (JNIEnv* env, jobject obj); / / the API for the hashCode method is defined and implemented in jvm.cpp / / hotspot\ src\ share\ vm\ jvm.cpp// java.lang.Object / / JVM_ENTRY (jint, JVM_IHashCode (JNIEnv* env, jobject handle) JVMWrapper ("JVM_IHashCode"); / / as implemented in the classic virtual machine Return 0 if object is NULL return handle = = NULL? 0: ObjectSynchronizer::FastHashCode (THREAD, JNIHandles::resolve_non_null (handle)); / / return 0 if object is null; otherwise, call ObjectSynchronizer::FastHashCodeJVM_END
Enter into ObjectSynchronizer::FastHashCode
/ / hotspot\ src\ share\ vm\ runtime\ synchronizer.cppintptr_t ObjectSynchronizer::FastHashCode (Thread * Self, oop obj) {/ /.... / / there is a key code in the FastHashCode method: if (mark- > is_neutral ()) {hash = mark- > hash (); / / first, retrieve hashCode if (hash) from the object's markword {/ / if it is fetched, return return hash;} hash = get_next_hash (Self, obj) directly / / if hashCode is not set in markword, call get_next_hash to generate hashCode temp = mark- > copy_set_hash (hash); / / the generated hashCode is set to markword / / use (machine word version) atomic operation to install the hash test = (markOop) Atomic::cmpxchg_ptr (temp, obj- > mark_addr (), mark); if (test = mark) {return hash;}} / /....}
The method get_next_hash for generating hashCode can support the generation of hashCode policies with different parameter configurations.
/ / hotspot\ src\ share\ vm\ runtime\ synchronizer.cppstatic inline intptr_t get_next_hash (Thread * Self, oop obj) {intptr_t value = 0; / / A total of 6 hashCode policies are supported. The default policy value is 5 if (hashCode = = 0) {/ / Policy 1: generate value = os::random () directly from random numbers } else if (hashCode = = 1) {/ / Policy 2: generate intptr_t addrBits = cast_from_oop (obj) > > 3 through object address and random number operations; value = addrBits ^ (addrBits > > 5) ^ GVars.stwRandom;} else if (hashCode = = 2) {/ / Policy 3: always return 1 for testing value = 1 / / for sensitivity testing} else if (hashCode = = 3) {/ / Strategy 4: returns a globally increasing sequence number value = + + GVars.hcSequence;} else if (hashCode = = 4) {/ / Policy 5: directly adopt the address value of object value = cast_from_oop (obj) } else {/ / Strategy 6: hashCode values are calculated by combining four variables in each thread: _ hashStateX, _ hashStateY, _ hashStateZ, _ hashStateW / /, and the four values unsigned t = Self- > _ hashStateX are modified synchronously according to the calculation results; t ^ = (t _ hashStateX = Self- > _ hashStateY; Self- > _ hashStateY = Self- > _ hashStateZ; Self- > _ hashStateZ = Self- > _ hashStateW Unsigned v = Self- > _ hashStateW; v = (v ^ (v > > 19)) ^ (t ^ (t > 8)); Self- > _ hashStateW = v; value = v;} value & = markOopDesc::hash_mask; / / obtain the final hashCode value if (value = 0) value = 0xBAD through the mask of hashCode; assert (value! = markOopDesc::no_hash, "invariant"); TEVENT (hashCode: GENERATE); return value;} 3. About the size of the hashCode value
Before and after being submitted to hashCode for generation, it is stored in markword. Let's take a closer look at this markword.
/ / hotspot\ src\ share\ vm\ oops\ markOop.hppclass markOopDesc: public oopDesc {private: / / Conversion uintptr_t value () const {return (uintptr_t) this } public: / / Constants enum {age_bits = 4, lock_bits = 2, biased_lock_bits = 1, max_hash_bits = BitsPerWord-age_bits-lock_bits-biased_lock_bits, hash_bits = max_hash_bits > 31? 31: max_hash_bits, / / by this definition Hashcode can occupy 31-bit bit. In 32-bit jvm, hashCode occupies 25 bits cms_bits = LP64_ONLY (1) NOT_LP64 (0), epoch_bits = 2};} 4. Verify package test;/*** * you can specify the hashCode generation policy through a series of parameters *-XX:hashCode=2 * / public class TestHashCode {public static void main (String [] args) {Object obj1 = new Object (); Object obj2 = new Object (); System.out.println (obj1.hashCode ()); System.out.println (obj2.hashCode ());}}
Through the form of-XX:hashCode=2, the hashCode generation strategy in the above 5 can be verified.
5. Summary
In 64-bit jvm, hashCode occupies up to 31 bit; 32-bit jvm, and hashCode occupies up to 25 bit
There are six generation strategies for hashCode.
The serial number hashCode policy value description 10 directly generates 21 through random numbers, generates 32 through the operation of object addresses and random numbers, and always returns 1 for test 43 to return a globally increasing sequence number 54 directly using the address value of object 6 other hashcode values are calculated through the combination of four variables in each thread: _ hashStateX, _ hashStateY, _ hashStateZ, _ hashStateW, and modify these four values according to the calculation results.
The default policy is policy 6, which is defined in the globals.hpp file
Product (intx, hashCode, 5,\ "(Unstable) select hashCode generation algorithm") Thank you for your reading, the above is the content of "how to use java Object's hashCode method". After the study of this article, I believe you have a deeper understanding of how to use java Object's hashCode method, and the specific use needs to be verified in practice. Here is, the editor will push for you more related knowledge points of the article, welcome to follow!
Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.
Views: 0
*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.
Continue with the installation of the previous hadoop.First, install zookooper1. Decompress zookoope
"Every 5-10 years, there's a rare product, a really special, very unusual product that's the most un
© 2024 shulou.com SLNews company. All rights reserved.