Object根类方法探析

本篇文章主要归纳java的根类Object类中的方法,它提供了11个方法,下面做简要总结。

1
2
3
4
5
6
7
8
9
10
11
public final native Class<?> getClass()
public native int hashCode()
public boolean equals(Object obj)
protected native Object clone() throws CloneNotSupportedException
public String toString()
public final native void notify()
public final native void notifyAll()
public final native void wait(long timeout) throws InterruptedException
public final void wait(long timeout, int nanos) throws InterruptedException
public final void wait() throws InterruptedException
protected void finalize() throws Throwable { }

getClass()

getClass方法是一个final方法,不允许子类重写,并且也是一个native方法。

Returns the runtime class of this {@code Object}

注意,这里返回的是运行时候对象的Class,比如以下代码中n是一个Number(抽象类)类型的实例,但是java中数值默认是Integer类型,所以getClass方法返回的是java.lang.Integer:

1
2
3
System.out.println("str".getClass() == String.class); // true
Number n = 0;
System.out.println(n.getClass());// class java.lang.Integer

hashCode()和equals(Object obj)

经常约定当重写equals()方法的时候,同时也需要重写hashCode()方法,网上有很多文章用了很多很长的篇幅介绍,但还是具有迷惑性。
其实是可以这么理解的,假设一个场景,我要对equals()方法进行重写,以便我调用equals()方法判断两个对象是否相等的时候,只要两个对象的id属性相同就返回true,便默认这两个对象相同。
但是这个时候,如果我不重写hashCode()方法,hashCode()便会产生两个不同的hashcode,这样便会产生一个逻辑上的矛盾。就是这两个对象都可以塞进类似于Set这样的集合中,但是我们明明调用了equals()方法判断他们是相同的。
所以这就解释了为什么,重写equals(Object obj)方法,必须同时重写hashCode()方法。
下面是jdk中javadoc的注释,最后一句话耐人寻味:

Note that it is generally necessary to override the hashCode method whenever this method is overridden, so as to maintain the general contract for the hashCode method, which states that equal objects must have equal hash codes.
equal的对象必须有相同的hash code。

clone()

创建并返回当前对象的一份拷贝。但是,对象必须要实现Cloneable接口才能调用clone方法,否则报错出现CloneNotSupportedException异常。
示例代码如下:

1
2
3
4
5
6
7
8
public class ObjectTest implements Cloneable{
public static void main(String[] args) throws CloneNotSupportedException {
ObjectTest c=new ObjectTest();
System.out.println(c==c.clone());//false
System.out.println(c.getClass()==c.clone().getClass());//true
}
}

toString()

Object对象的默认实现,即输出类的名字@实例的哈希码的16进制:

1
2
3
public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}

很简单,可以重写,IDE工具什么的都自带这个方法的重写。

finalize()

默认实现代码如下:

1
protected void finalize() throws Throwable { }

我们还是看javadoc的注释,如下:

Called by the garbage collector on an object when garbage collection determines that there are no more references to the object.A subclass overrides the {@code finalize} method to dispose of system resources or to perform other cleanup.

该方法的作用是实例被垃圾回收器回收的时候触发的操作,就好比 “死前的最后一波挣扎”,用来完成一些系统资源回收或者其他的一些清理工作之类的。

最后Object方法还有下面几个方法notify()notifyAll()wait()没有归纳,但是都是跟线程相关的方法,等到跟java线程一块复习的时候再总结吧,就酱紫。

-EOF-