天天看点

深入分析Java中打印对象内存地址

地址是什么样子的

我们知道system.out.println(new XXX())可以打印出

内存地址

我们看个例子:

public class Test {
    public static void main(String[] args) {
        Test t = new Test();
        System.out.println(t);
           

看下输出的结果:

[email protected]
           

toString()方法

这个结果是怎么来的呢,其实是调用了Test的

toString()

方法,该方法继承自

Object

public class Object {
    public String toString() {
        return getClass().getName() + "@" + Integer.toHexString(hashCode());
    }
    public native int hashCode();
           

看到这里,toString方法其实是打印了对象自身的hashCode,Object的hashCode() 是一个

native

方法,默认返回的是

内存地址

。toString方法打印不是hashCode()返回的原值,而是经过转化的

16进制字符

重写hashCode

我们知道,hashCode()可以重写,如果重写的话,同一个类型的2个实例,

hashCode

的值是

相同

的,但是

地址

肯定是

不相同

的,此时,如果想打印出地址怎么办?这时,不能直接调用hashCode了

我们再看个例子:

public class TestMem {
    public static void main(String[] args) {
        String s1 = "hello";
        String s2 = "world";
        String s3 = "helloworld";
        String s4 = s1+s2;
         System.out.println(s3.equals(s4));
        System.out.println(s3==s4);
        System.out.println(s3.hashCode());
        System.out.println(s4.hashCode());
        System.out.println(System.identityHashCode(s3));
        System.out.println(System.identityHashCode(s4));
 
    }
}
           

结果:

true         //字面值相同
false        //地址不同
-1524582912  //对比2个发现hashcode相同
-1524582912  
1284693
31168322
           

通过结果,我们发现s3和s4的字面值是相同的,但地址是不相同的,字面值相同是因为String类虽然继承了Object,但是重写了hashcode,地址不同可以通过

identityHashCode

打印出来