Java中Class和Object是什么意思

您所在的位置:网站首页 编程中shell是什么意思 Java中Class和Object是什么意思

Java中Class和Object是什么意思

#Java中Class和Object是什么意思| 来源: 网络整理| 查看: 265

如果一个没有直接父类接口,接口声明了一个public abstract方法m,JVM将会为接口标隐含定义了Object类中的方法签名完全相同的方法。除非在接口明确的定义了在接口中定义了同样方法签名,同样返回值以及throws同样的异常。

但是要注意以下两点:

如果在接口中定义了与Object定义相同的方法,并且声明为final。那么就会出现编译异常。

如果在接口中定义了与Object定义签名相同的方法。但是它不符合Object的重写规范那。就是返回值类型不同,或者抛出不兼容的异常,或者不是abstract的方法。也会出现编译异常。

      2、Object中的方法

下面我们就来看一看Object里面的方法。Object作为通用的类,作为通用的类不能够满足于各种各样的业务场景,所以对于它所有的非final方法(equals、hashcode、toString、clone和finalize)都有明确的通用约定,因为它们的设计成是要被覆盖的。任何一个类,它在覆盖这些方法的时候,都有责任遵守这些通用约定,其他依赖于这些约定的类(例如HashMap和HashSet)就无法结合该类一起正常工作了。

      2.1 getClass – 获取当前对象的类类型

获取当前对象的类类型,使用这个对象可以执行反射操作。

      2.2 hashCode – 获取当前对象的hashCode

返回当前对象的hash code值。当这个对象需要使用到hash表的时候需要重写这个方法。同时也需要重写equals方法。

      2.3 equals – 判断两个对象是否相等

表明其它对象是否写当前对象相等。默认是判断两个对象的引用地址是否相等。而在Effective Java中推荐覆盖equals方法的时候总要覆盖hashCode方法。而需要覆盖equals方法的时候需要遵守它的通用规定。下面就约定的内容:

自反性(reflexive):对于任何非null的引用值x,x.equals(x)必须返回true.

对称性(symmetric):对于任何非null的引用值x,y,当且仅当y.equals(x)返回true时x.equals(y)必须返回true。

传递性(transitive):对于任何非null的引用值x,y,z。如果x.equals(y)返回true.并且y.equals(z)也返回true,那么x.equals(z)也必须返回true.

一致性(consistent):对于任何非null的引用值x和y,只要equals的比较操作在对象中所用的信息没有被修改,多次调用x.equals(y)就会一致地返回true,或者一致地false。

对于任何非null的引用值x,x.equals(null)必须返回false

      2.4 clone – 对象克隆

创建并且返回这个对象的copy。精确的表达”copy”依赖于该对象的类。一般情况下,对于对象x:

表达式:x.clone() != x,将会为true

表达式:x.clone().getClass() == x.getClass(),将会为true

表达式:x.clone().equals(x),将会为true. 默认情况下满足这种情况,但这个并不是绝对的。 按照约定:一般通过调用super.clone获取到返回对象。如果一个类以及它的所有超类就会出现:x.clone().getClass() == x.getClass().

而且Object类并没有实现Cloneable接口。因此如果一个类并没有实现Cloneable接口,而且它的实例还调用clone方法就会出现CloneNotSupportedException.

      2.5 toString – 返回代表这个对象的String

虽然java.lang.Object提供了toString方法的一个实现,但它返回的是类的名称以及一个”@”符号,接着是散列码的无符号十六进制表示法。例如:Object@163b91,这种表示方法对于用户是非常不友好的。所以toString的约定是:建议所有的子类都覆盖这个方法。

      2.6 notify – 唤醒被当前线程监控正在等待的一个线程

唤醒被当前线程监控正在等待的一个线程。如果有这个对象中许多线程正在等待,就会从它们中选择一个来唤醒。这个选择是根据各个不同的系统来任意决定的,也就是说多个线程在waiting是随机选择一个线程来唤醒。

这个方法仅仅能够被是这个对象的monitor调用。一个线程可以通过以下3种方式来成为这个对象的monitor的拥有者。

执行这个对象的同步实例方法。

执行这个对象的同步代码块。

对于Class对象,执行一个同步静态方法。

并且在同一时间只能有一个线程做为一个对象minitor的拥有者。 

      2.7 notifyall – 唤醒被当前线程监控正在等待所有线程

唤醒被当前线程监控正在等待所有线程。如果是一个线程被这个对象monitor的话,可以调用wait方法。

这个方法也仅难能被这个对象的monitor的拥有者调用。具体可以看一下notity方法中介绍一个线程如何才能够成功一个monitor的拥有者。

      2.8 wait() || wait(long) || wait(long, int)

这三个方法的功能都是一样的,都是让线程进入等待状态。只是等待的超时时间的设置方式不同。调用这三个方法都是暂停当前线程,直到另外一个线程调用notify方法或者notifyall方法或者其它线程中断了当前线程,或者过了超时时间。

      2.9 finalize – 调用这个对象的垃圾回收

当没有引用指向这个对象的时候,调用这个对象的垃圾回收。子类可以重写finalize方法用来处理系统资源或者执行其它清除操作。

一般情况下当JVM确定这个对象没有被其它对象引用的时候,就会调用finalize方法。一般的纯Java编写的Class不需要重新覆盖这个方法,因为Object已经实现了一个默认的,除非我们要实现特殊的功能(这 里面涉及到很多东西,比如对象空间树等内容)。

不过用Java以外的代码编写的Class(比如JNI,C++的new方法分配的内存),垃圾回收器并不能对这些部分进行正确的回收,这时就需要我们覆盖默认的方法来实现对这部分内存的正确释放和回收(比如C++需要delete)。

总之,finalize相当于析构函数,他是垃圾回收器回收一个对象的时候第一个要调用的方法。不过由于Java的垃圾回收机制能自动为我们做这些事情,所以我们在一般情况下是不需要自己来手工释放的。

      3、Object 与 Class

先有Class还是先有Object? Java的对象模型中:

所有的类都是Class类的实例,Object是类,那么Object也是Class类的一个实例。

所有的类都最终继承自Object类,Class是类,那么Class也继承自Object。



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3