其他方法
概述
Object 还有一些不太常用但同样重要的方法:getClass()、clone() 和已废弃的 finalize()。
getClass()
基本使用
getClass() 返回对象的运行时类,不能被重写。
java
Object obj = new Person("张三", 25);
Class<?> clazz = obj.getClass();
System.out.println(clazz.getName()); // com.example.Person
System.out.println(clazz.getSimpleName()); // Person
System.out.println(clazz.getPackage().getName()); // com.example反射应用
java
Object obj = getObject();
Class<?> clazz = obj.getClass();
// 获取所有方法
for (Method m : clazz.getDeclaredMethods()) {
System.out.println(m.getName());
}
// 获取所有字段
for (Field f : clazz.getDeclaredFields()) {
System.out.println(f.getName() + " : " + f.getType().getSimpleName());
}clone()
基本使用
clone() 创建对象的副本。需要类实现 Cloneable 接口。
java
class Address implements Cloneable {
private String city;
@Override
protected Address clone() throws CloneNotSupportedException {
return (Address) super.clone();
}
}
Address original = new Address("北京");
Address copy = original.clone();
original == copy; // false,不同对象
original.getCity() == copy.getCity(); // true,String 在常量池浅拷贝 vs 深拷贝
java
class Person implements Cloneable {
private String name; // 不可变对象
private Address address; // 可变对象
@Override
protected Person clone() {
try {
Person p = (Person) super.clone();
// 浅拷贝:address 还是同一个引用
// p.address == this.address // true
// 深拷贝:复制一份
p.address = this.address.clone();
return p;
} catch (CloneNotSupportedException e) {
throw new RuntimeException(e);
}
}
}为什么不常用?
- 需要实现 Cloneable 接口
- 只能浅拷贝
- 访问修饰符 protected
- 返回 Object,需要强制转型
- 性能一般
替代方案:拷贝构造器或工厂方法
java
class Person {
private String name;
// 拷贝构造器
public Person(Person other) {
this.name = other.name;
}
}
// 使用
Person copy = new Person(original);finalize()(已废弃)
什么是 finalize()
finalize() 在对象被垃圾回收前调用,用于释放资源。
java
class Resource {
private FileHandle handle;
@Override
protected void finalize() throws Throwable {
if (handle != null) {
handle.close();
}
}
}为什么废弃?
- 调用时机不确定:GC 不一定会马上执行
- 性能开销:GC 要额外处理 finalize
- 资源泄漏:如果 finalize 执行失败,资源可能泄漏
- 线程不确定:finalize 在哪个线程执行都不确定
替代方案
java
// 方式一:try-with-resources
class Resource implements AutoCloseable {
@Override
public void close() {
// 释放资源
}
}
try (Resource r = new Resource()) {
// 使用资源
} // 自动调用 close()总结
| 方法 | 说明 | 推荐 |
|---|---|---|
| getClass() | 获取运行时类型 | 反射时常用 |
| clone() | 对象拷贝 | 拷贝构造器更好 |
| finalize() | 垃圾回收前调用 | 不要用 |
实际开发中,getClass() 用于反射场景,finalize() 完全不应该使用。
