请看下面的图片。当我们在java中创建一个带有new关键字的对象时,我们从操作系统中获得了一个内存地址。当我们写out.println(objName)时,我们可以看到一个“特殊”字符串作为输出。1.这是什么输出?1.如果是OS给我们的内存地址:a)如何将此字符串转换为二进制?B)如何获取一个整型变量的地址?
new
out.println(objName)
rsaldnfx1#
这是由'@'字符分隔的类名和System.identityHashCode()。标识散列代码所代表的是特定于实现的。它通常是对象的初始内存地址,但对象可以随着时间的推移在内存中移动。所以(简单地说)你不能依赖于它是任何东西。获取变量的内存地址在Java中是没有意义的,因为JVM可以自由地实现对象并在合适的时候移动它们(在垃圾收集等过程中,对象可能/将移动)。toBinaryString()将为您提供二进制形式的整数。
jpfvwuh42#
可以使用sun.misc.Unsafe:请看@Peter Lawrey的精彩回答-〉Is there a way to get a reference address?将其代码用于printAddresses():
sun.misc.Unsafe
public static void printAddresses(String label, Object... objects) { System.out.print(label + ": 0x"); long last = 0; int offset = unsafe.arrayBaseOffset(objects.getClass()); int scale = unsafe.arrayIndexScale(objects.getClass()); switch (scale) { case 4: long factor = is64bit ? 8 : 1; final long i1 = (unsafe.getInt(objects, offset) & 0xFFFFFFFFL) * factor; System.out.print(Long.toHexString(i1)); last = i1; for (int i = 1; i < objects.length; i++) { final long i2 = (unsafe.getInt(objects, offset + i * 4) & 0xFFFFFFFFL) * factor; if (i2 > last) System.out.print(", +" + Long.toHexString(i2 - last)); else System.out.print(", -" + Long.toHexString( last - i2)); last = i2; } break; case 8: throw new AssertionError("Not supported"); } System.out.println(); }
我设置了这个测试:
//hashcode System.out.println("Hashcode : "+myObject.hashCode()); System.out.println("Hashcode : "+System.identityHashCode(myObject)); System.out.println("Hashcode (HEX) : "+Integer.toHexString(myObject.hashCode())); //toString System.out.println("toString : "+String.valueOf(myObject)); printAddresses("Address", myObject);
以下是输出:
Hashcode : 125665513 Hashcode : 125665513 Hashcode (HEX) : 77d80e9 toString : java.lang.Object@77d80e9 Address: 0x7aae62270
结论:
bq9c1y663#
这是Object的“toString()”实现的输出。如果你的类覆盖了toString(),它将打印出完全不同的内容。
wqnecbli4#
这是不是内存地址这是类名@哈希码Object.toString()的默认实现是什么?
Object.toString()
public String toString() { return getClass().getName() + "@" + Integer.toHexString(hashCode()); }
其中Class name =完全限定名或绝对名(即包名后接类名)hashcode =十六进制格式(System.identityHashCode(obj)或obj.hashCode()将以十进制格式为您提供散列代码)。提示:产生混淆的根本原因是Object.hashCode()的默认实现使用了将对象的内部地址转换为整数这通常是通过将对象的内部地址转换为整数来实现的,但Java™编程语言并不需要这种实现技术。当然,有些类可以覆盖toString()或hashCode()的两种默认实现如果您需要覆盖hashcode()的对象的默认实现值,可以使用以下方法System.identityHashCode(Object x)
Class name
hashcode
Object.hashCode()
toString()
hashCode()
hashcode()
System.identityHashCode(Object x)
6rqinv9w5#
就像Sunil说的,这不是内存地址。这只是散列码要获得相同的@内容,您可以:如果在该类中未覆盖hashCode:
"@" + Integer.toHexString(obj.hashCode())
如果hashCode被覆盖,则使用以下语句获取原始值:
"@" + Integer.toHexString(System.identityHashCode(obj))
这通常会与内存地址混淆,因为如果不覆盖hashCode(),则会使用内存地址来计算哈希。
kcwpcxri6#
您得到的是Object类的toString()方法的结果,或者更准确地说,是uzay95指出的identityHashCode()的结果。“当我们使用new关键字在java中创建一个对象时,我们将从操作系统中获取一个内存地址。”在Java中所做的一切都是由Java虚拟机来处理的,这一点很重要。JVM提供了这些信息。主机操作系统的RAM中实际发生的情况完全取决于JRE的实现。
ffx8fchx7#
了解java中散列码是很有用的:http://eclipsesource.com/blogs/2012/09/04/the-3-things-you-should-know-about-hashcode/
up9lanfz8#
根据Javadoc的Printing对象引用,它将返回对象的字符串表示形式,因为它将在内部调用Object类的toString()方法。enter image description here
eufgjt7s9#
在Java中,当你从Person p = new Person();这样的类中创建一个对象时,p实际上是一个内存位置的地址,它指向Person类型。当使用statemenet打印p时,您将看到一个地址。new关键字创建一个新的内存位置,其中包含所有包含在class Person中的示例变量和方法,p是指向该内存位置的引用变量。
Person p = new Person();
p
Person
class Person
9条答案
按热度按时间rsaldnfx1#
这是由'@'字符分隔的类名和System.identityHashCode()。标识散列代码所代表的是特定于实现的。它通常是对象的初始内存地址,但对象可以随着时间的推移在内存中移动。所以(简单地说)你不能依赖于它是任何东西。
获取变量的内存地址在Java中是没有意义的,因为JVM可以自由地实现对象并在合适的时候移动它们(在垃圾收集等过程中,对象可能/将移动)。
toBinaryString()将为您提供二进制形式的整数。
jpfvwuh42#
可以使用
sun.misc.Unsafe
:请看@Peter Lawrey的精彩回答-〉Is there a way to get a reference address?将其代码用于printAddresses():
我设置了这个测试:
以下是输出:
结论:
bq9c1y663#
这是Object的“toString()”实现的输出。如果你的类覆盖了toString(),它将打印出完全不同的内容。
wqnecbli4#
这是不是内存地址这是类名@哈希码
Object.toString()
的默认实现是什么?其中
Class name
=完全限定名或绝对名(即包名后接类名)hashcode
=十六进制格式(System.identityHashCode(obj)或obj.hashCode()将以十进制格式为您提供散列代码)。提示:
产生混淆的根本原因是
Object.hashCode()
的默认实现使用了将对象的内部地址转换为整数这通常是通过将对象的内部地址转换为整数来实现的,但Java™编程语言并不需要这种实现技术。
当然,有些类可以覆盖
toString()
或hashCode()
的两种默认实现如果您需要覆盖
hashcode()
的对象的默认实现值,可以使用以下方法
System.identityHashCode(Object x)
6rqinv9w5#
就像Sunil说的,这不是内存地址。这只是散列码
要获得相同的@内容,您可以:
如果在该类中未覆盖hashCode:
如果hashCode被覆盖,则使用以下语句获取原始值:
这通常会与内存地址混淆,因为如果不覆盖hashCode(),则会使用内存地址来计算哈希。
kcwpcxri6#
您得到的是Object类的toString()方法的结果,或者更准确地说,是uzay95指出的identityHashCode()的结果。
“当我们使用new关键字在java中创建一个对象时,我们将从操作系统中获取一个内存地址。”
在Java中所做的一切都是由Java虚拟机来处理的,这一点很重要。JVM提供了这些信息。主机操作系统的RAM中实际发生的情况完全取决于JRE的实现。
ffx8fchx7#
了解java中散列码是很有用的:
http://eclipsesource.com/blogs/2012/09/04/the-3-things-you-should-know-about-hashcode/
up9lanfz8#
根据Javadoc的Printing对象引用,它将返回对象的字符串表示形式,因为它将在内部调用Object类的toString()方法。enter image description here
eufgjt7s9#
在Java中,当你从
Person p = new Person();
这样的类中创建一个对象时,p
实际上是一个内存位置的地址,它指向Person
类型。当使用statemenet打印
p
时,您将看到一个地址。new
关键字创建一个新的内存位置,其中包含所有包含在class Person
中的示例变量和方法,p
是指向该内存位置的引用变量。