Java基础10
Object类
类java.lang.Object是类层次结构的根类,即所有其它类的父类。每个类都使用Object作为超类。
注意:
> Object类中声明的结构(属性、方法等)就具有通用性。
> Object类中没有声明属性
> Object类提供了一个空参的构造器
> 重点关注: Object类中声明的方法
常用方法
重点方法: equals() \ toString()
了解方法: clone() \ finalize()
后续了解的方法:getClass() \ hashCode() \ notify() \ notifyAll() \ wait() \ wait(xx) \ wait(xx,yy)
clone()
clone()
方法是用来创建并返回此对象的一个副本的。换句话说,它可以帮助我们复制一个对象。
前提:只有实现了Cloneable
接口的类才能被复制,否则调用clone()
方法时会抛出CloneNotSupportedException
异常
// 定义一个实现了Cloneable接口的类 class MyClass implements Cloneable { int value; public MyClass(int value) { this.value = value; } // 重写Object类的clone()方法 @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); } @Override public String toString() { return "MyClass{" + "value=" + value + '}'; } } public class Main { public static void main(String[] args) { try { MyClass obj1 = new MyClass(10); MyClass obj2 = (MyClass) obj1.clone(); // 复制对象 System.out.println("obj1: " + obj1); // 输出:obj1: MyClass{value=10} System.out.println("obj2: " + obj2); // 输出:obj2: MyClass{value=10} System.out.println("obj1 == obj2: " + (obj1 == obj2)); // 输出:obj1 == obj2: false,说明两个对象在内存中的地址不同 } catch (CloneNotSupportedException e) { e.printStackTrace(); } } }
定义了一个实现了Cloneable接口的类MyClass,并重写了clone()方法。
在main方法中,我们创建了一个MyClass对象obj1,并使用clone()方法复制了obj1得到了obj2。通过输出我们可以看到,obj1和obj2的值是一样的,但是它们在内存中的地址是不同的,说明它们是两个不同的对象。
finalize()
当垃圾回收器确定不存在对该对象的更多引用时,对象的垃圾回收器将调用此方法
注意:finalize()
方法并不能保证一定会被执行,也不能保证何时被执行。因此,我们不能依赖finalize()
方法来执行一些重要的清理工作,比如关闭文件、断开网络连接等
class MyClass { @Override protected void finalize() throws Throwable { System.out.println("MyClass对象被垃圾回收器回收了"); super.finalize(); // 调用父类的finalize()方法 } } public class Main { public static void main(String[] args) { MyClass obj = new MyClass(); obj = null; // 将obj引用置为null,使得原来的MyClass对象可以被垃圾回收器回收 // 在这里,我们并不能确定MyClass对象的finalize()方法是否已经被执行,因为垃圾回收器的行为是不可预测的 } }
定义了一个类MyClass,并重写了finalize()方法。在main方法中,我们创建了一个MyClass对象obj,然后立即将obj引用置为null,使得原来的MyClass对象可以被垃圾回收器回收。但是,我们不能确定MyClass对象的finalize()方法是否已经被执行,因为垃圾回收器的行为是不可预测的。
equals()
java.lang.Object类中equals()的定义:
public boolean equals(Object obj){ return (this == obj); }
说明
> 自定义的类在没有重写Object中的equals()方法的情况下,调用的就是Object类中声明的equals(),比较两个对象的引用地址是否相同。(或比较两个对象是否指向了堆空间中的同一个对象实体)
> 对于像String、File、Data和包装类等,它们都重写了Object类中的equals()方法,用于比较两个对象的实体内容是否相等。
package com.atgjwqz.exercise; public class UserTest { public static void main(String[] args) { User u1 = new User("Tom", 12); User u2 = new User("Tom",12); System.out.println(u1.equals(u2)); //输出:false 判断的是地址值 String str1 = new String("hello"); String str2 = new String("hello"); System.out.println(str1 == str2);// false System.out.println(str1.equals(str2)); //true } } class User{ String name; int age; public User() { } public User(String name, int age) { this.name = name; this.age = age; } }
开发中的使用说明
> 实际开发中,针对于自定义的类,常常会判断两个对象是否equals(),而此时主要是判断两个对象的属性值是都相等,所以要重写Object类的equals()方法。
> 如何重写: ① 手动自己实现 ② 调用IDEA自动实现(推荐)
区分== 和 equals()
==:运算符
① 适用范围: 基本数据类型、引用数据类型
② 基本数据类型:判断数据值是否相等
char c1 = 'A'; int i1 = 65; sout(c1 == i1); //true c1的类型会自动提升为int然后比较 float f1 = 12.0F; int i2 = 12; sout(f1 == i2); //true int类型自动提升为float
引用数据类型变量:比较两个引用变量的地址值是否相等。(或比较两个引用是否指向同一个对象实体)
equals():方法
> 使用范围:只能使用在引用数据类型上。
> 具体使用:对于类来说,重写equals()和不重写equals()的区别。
案例:
编写Order类,有int型的orderId,String型的orderName,相应的getter()和setter()方法,两个参数的构造器。
重写父类的equals()方法:public boolean equals(Object obj),并判断测试类中创建的两个对象是否相等
public class Order { int orderId; String orderName; public Order(int orderId, String orderName) { this.orderId = orderId; this.orderName = orderName; } public int getOrderId() { return orderId; } public void setOrderId(int orderId) { this.orderId = orderId; } public String getOrderName() { return orderName; } public void setOrderName(String orderName) { this.orderName = orderName; } @Override public boolean equals(Object obj) { if(this == obj){ return true; } if (obj instanceof Order){ Order order = (Order) obj; if(this.orderId == order.orderId && this.orderName == orderName) { return true; } } return false; } }
public class OrderTest { public static void main(String[] args) { Order o1 = new Order(1001,"orderAA"); Order o2 = new Order(1001,"orderAA"); System.out.println(o1.equals(o2)); //true } }