。看來獲得這個引用的唯一方法是調用toString()方法,它返回對象哈希碼而不是地址。
hashCode是一個隨機生成的數字,與地址無關。
有沒有辦法獲得對象的物理地址?
你可以用不安全的方式得到它,但是除了興趣外,你不應該這樣做。
JVM如何找到對象?
JVM使用該引用作爲索引。該索引可以是間接的,即可以有一個對象所在的陣列,它可以是例如一個翻譯。 CompressedOops可能會將索引乘以8,並可以選擇添加偏移量。
如果使用Oracle/OpenJDK並禁用CompressedOops,則可以獲得未翻譯的64位地址。
一個簡單的方法做,這是把對象的地址到一個數組 ,然後就好像他們根據你的推薦尺寸爲int
或long
訪問數組中的元素。
Object i = 0x12345678;
System.out.printf("indentityHashCode = %08x%n", System.identityHashCode(i));
Object[] obj = {i};
assert Unsafe.ARRAY_OBJECT_INDEX_SCALE == 8; // 8 bytes per reference.
long address = UNSAFE.getLong(obj, (long) Unsafe.ARRAY_OBJECT_BASE_OFFSET);
System.out.printf("%x%n", address);
for (int j = 0; j < 24; j++)
System.out.printf("%02x ", UNSAFE.getByte(address + j) & 0xFF);
System.out.println();
// now some really scary sh!t
UNSAFE.putLong(i, 8L, UNSAFE.getLong(0L, 8L));
System.out.printf("`i` is now a %s and is %x%n", i.getClass(), i);
我有很多其他的例子在這裏
https://github.com/peter-lawrey/Performance-Examples/tree/master/src/main/java/vanilla/java/unsafe
最有用的技巧是能夠看見物體是如何排列,前後GC之後。只能在家裏嘗試。 NSFW。
請澄清您的具體問題或添加其他詳細信息,以確切地突出顯示您的需求。正如目前所寫,很難確切地說出你在問什麼。請參閱如何問問頁面以獲取幫助以澄清此問題。 –
對象的物理地址不可訪問,並且可以由JVM隨意更改。 toString()中的「地址」是*身份哈希*,與地址不同。 – Bohemian
您可以使用'sun.misc.Unsafe'來獲取對象的當前物理地址(http://stackoverflow.com/questions/38114099/understanding-how-to-memcpy-with-theunsafe/38189553#38189553)。但垃圾收集器可能會在當時踢,並將對象移動到其他地址。所以你得到的地址可能幾乎從你得到它的那一刻起就失效了。 –