ObJect类源码分析

1. getClass方法public final native Class<?> getClass();

getClass方法返回对象运行时的类,即返回的是动态类型的类
Java不是存粹的静态类型或者动态类型,A a,A就是静态类型,若B继承于A,a = new B(),B就是动态类型。

可以通过以下例子看出getClass方法的返回。。

A a = new A();
A b = new B();
B c = new B();
System.out.println(a.getClass().getName());
System.out.println(b.getClass().getName());
System.out.println(c.getClass().getName());

//结果如下:
test.A
test.B
test.B

2. hashCode()方法
  1. hashCode方法返回对象的哈希值,它的存在是为了提高HashTable、HashMap等的效率。
    重写hashCode的原则
  2. 对于同一对象,在不改变equals方法前提下,必须返回相同的哈希值。
  3. 对于equals方法返回true的两个对象,哈希值必须返回相同的。
  4. 对于equals方法返回false的两个对象,哈希值可以相同也可以不相同,但是我们应该尽量让他们的哈希值不相同。
3. equals()方法

比较两个对象的相等性,是比较的是两个对象的内存地址
其底层是使用了“==”来实现,
也就是说通过比较两个对象的内存地址是否相同判断是否是同一个对象。

   public boolean equals(Object obj) {
        return (this == obj);
    }
Why重写equals方法必须重写hashCode()方法

先说为什么要重写equals方法?
因为equals底层实现是==来比较内存地址,但是在实际应用中,该方法不能满足的我们的需求。因为我们认为两个对象即使不是指向的同一块内存,只要这两个对象的各个字段属性值都相同,那么就认为这两个对象是同一个对象。所以就需要重写equals()方法,即如果两个对象指向内存地址相同或者两个对象各个字段值相同,那么就是同一个对象。

回到问题,为什么需要重写hashcode

  1. hashCode()方法是一个本地native方法,返回的是对象引用中存储的对象的内存地址
  2. 而equals方法是利用==来比较的也是对象的内存地址。
  3. 假设两个对象,重写了其equals方法,其相等条件是属性相等,就返回true。
  4. 如果不重写hashcode方法,其返回的依然是两个对象的内存地址值,必然不相等。
  5. 这就出现了equals方法相等,但是hashcode不相等的情况。这不符合hashcode的规则。

实际的意义
在Java中的一些容器(如:set)中,不允许有两个完全相同的对象,插入的时候,如果判断相同则会进行覆盖。这时候如果只重写了equals()的方法,而不重写hashcode的方法,Object中hashcode是根据对象的存储地址转换而形成的一个哈希值。这时候就有可能因为没有重写hashcode方法,造成相同的对象散列到不同的位置而造成对象的不能覆盖的问题。

怎么重写两个方法

        public class SimpleDemo {
	// 部门
	private String department;
	// 工号
	private int id;
 
	public SimpleDemo(int id, String department) {
		super();
		this.id = id;
		this.department = department;
	}
 
	public int getId() {
		return id;
	}
 
	public void setId(int id) {
		this.id = id;
	}
 
	public String getdepartment() {
		return department;
	}
 
	public void setdepartment(String department) {
		this.department = department;
	}
 
	@Override
	public int hashCode() {
		int hash = 1;
		hash = hash * 17 + id;
		hash = hash * 31 + department.hashCode();
		return hash;
	}
       @Override
	public boolean equals(Object obj) {
		if (obj == null)
			return false;
		if (obj == this)
			return true;
			//如果两个的参数什么都相同,即使是不同的对象也判断相等
		if (obj instanceof SimpleDemo) {
			SimpleDemo sd = (SimpleDemo) obj;
			return sd.department.equals(department) && sd.id == id;
		}
		return false;
	}
     public class Test02 {
	  public static void main(String[] args) {
		SimpleDemo sdo1=new SimpleDemo(0106,"技术部");
		SimpleDemo sdo2=new SimpleDemo(0106,"技术部");
                //print true
                //重写后让参数相同的两个对象相等了
               System.out.println(sdo1.equals(sdo2));
	}
}

再说一些
一般String都是重写了equals方法的

String如何判断=
1. 对象是否相同,相同true
2. 长度是否相同
3. 遍历char数组,如果char数组每个元素都相同,判断true
//String重写的equals方法
    public boolean equals(Object anObject) {
        if (this == anObject) {
            return true;
        }
        if (anObject instanceof String) {
            String anotherString = (String)anObject;
            int n = value.length;
            if (n == anotherString.value.length) {
                char v1[] = value;
                char v2[] = anotherString.value;
                int i = 0;
                while (n-- != 0) {
                    if (v1[i] != v2[i])
                        return false;
                    i++;
                }
                return true;
            }
        }
        return false;
    }

//String重写的hashcode方法
  public int hashCode() {
        int h = hash;
        if (h == 0 && value.length > 0) {
            char val[] = value;

            for (int i = 0; i < value.length; i++) {
                h = 31 * h + val[i];
            }
            hash = h;
        }
        return h;
    }
4. clone()方法

clone方法返回一个对象的复制。使用克隆方法的类必须实现Cloneable接口,否则会抛出CloneNotSupportedException异常。

  protected native Object clone() throws CloneNotSupportedException;

5. ToString()方法

toString方法返回对象的字符串。如果我们自己的类没有重写toString方法,就会返回类名加类的哈希值的16进制的表示。

  public String toString() {
        return getClass().getName() + "@" + Integer.toHexString(hashCode());
    }
6. notify() 、notifyAll、wait、
7. finalize()

当垃圾回收器认为一个对象没有其他引用时,就调用finalize()方法清理对象。

   protected void finalize() throws Throwable { }
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Object.assign是JavaScript中的一个方法,用于将一个或多个对象中的所有可枚举属性复制到一个目标对象中。这个方法是浅拷贝的,只会复制对象的属性的值,不会复制对象的原型链。下面是对Object.assign码的分析Object.assign的定义如下: ```javascript Object.assign(target, ...sources) ``` 首先,我们分析码中对于参数的处理。首先检查目标对象是否为null或undefined,如果是,则抛出一个TypeError。然后检查对象是否为null或undefined,如果是,则直接返回目标对象。接下来,通过Object()方法将目标对象转换为一个Object类型的对象。然后使用剩余参数语法将所有对象放入一个数组中。 接下来,针对每个对象,通过Object()方法将其转换为一个Object类型的对象。然后使用for...in循环遍历每个对象的可枚举属性,并将其复制到目标对象中,使用hasOwnProperty()方法判断属性是否来自对象本身而不是原型链。在这个过程中,如果目标对象中已经存在同名属性,则会被对象中的属性值覆盖。 最后,返回修改后的目标对象。 需要注意的是,Object.assign只会对对象的属性进行浅拷贝。如果对象的属性值是对象或数组,那么目标对象中的对应属性也会引用同一个对象或数组。 总结一下,Object.assign是一个用于将一个或多个对象的可枚举属性复制到目标对象中的方法。它通过遍历对象的属性并将其复制到目标对象中来实现。在使用过程中需要注意浅拷贝带来的引用问题。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值