22、Object类和Set集合

22_Object 类和 Set 集合

1、Object 类
1.1 Object 类概述
	Java 中所有类的基类,Java 中任何一个类都是 Object 类的子类或者间接子类。Object 类内提供的方法所有类都可以使用。
	目前需要了解的三类方法:
		1、比较相关
			boolean equals(Object obj);
				判断参数对象和调用方法的对象是否为同一个对象
			int hashCode();
				获取当前对象的哈希值
		2、线程相关
			wait();
			wait(int ms);
			notify();
			notifyAll();
		3、数据字符串描述相关
			String toString();
				提供当前对象的字符串信息描述
1.2 重写 equals()
流程
	1、判断参数对象和调用方法的对象是否为同一个对象(指向同一个地址),若是同一个对象,返回true;
	2、若不是同一个对象,继续判断当前参数对象和调用方法的对象是否是同一个数据类型,若不是同一个类型,返回false;
	3、若是同一个类型,继续判断参数对象和调用方法的对象的数据内容是否完全相同,若完全相同返回true,否则返回false。
	public boolean equals(Object obj) {
		//1、判断调用方法的对象和参数对象是否为同一个即【同地址】对象
		if (this == obj) {
			return true;
		}
		
		/*
		 * 2、判断调用方法的对象和参数对象是否为同一个类型
		 * 
		 * instanceof 关键字 判断当前对象类型是否为当前类型
		 */
		if (!(obj instanceof Student)) {
			return false;
		}
		
		//3、进行对象数据内容判断
		//3.1 强制类型转换
		Student stu = (Student)obj;
		
		/*
		 * 3.2 比较方法调用的对象和参数对象的内容是否一致
		 * 
		 * int id			==
		 * String name		字符串判断方法 equals()
		 * int age			==
		 */
		return id == stu.id 
				&& name.equals(stu.name)
				&& age == stu.age;
	}
1.3 重写 hashCode()
		Java 中要求:如果两个对象使用 equals() 判断结果为 true,证明两个对象实际上是同一个对象,那么两个对象调用 hashCode()
	得到的哈希值必须一致。
		hashCode() 在没有重写的情况下,默认返回值数据是当前对象在内存中的存储数据的地址内容(十进制表示),该数据具备唯一
	性,可以作为身份标识。 
	/*
	 * 证明两个对象为同一个对象 
	 * 规定通过 hashCode() 得到的哈希值必须一致
	 */
	@Override
	public int hashCode() {
		/*
		 * Object 的工具类 Objects 中的方法 hash(Object...values)
		 * 
		 * Object...
		 * 不定长参数 需要提供的数据类型必须是 Object 类型 等价于 Java中任意的数据类型都支持
		 * 方法体中是 Object[]
		 * 
		 * hash(Object...values)
		 * 根据内容返回哈希值
		 */
		return Objects.hash(id, name, age);
	}
2、Set 集合
2.1 Set 集合概述
	Set 集合的方法都来自于 Collection 集合 没有特征方法

	Set 集合特征:
		1、无序
		2、不可重复

	Set 集合接口的两个实现类
		1、class HashSet
			底层结构为 哈希表结构,要求添加数据必须有比较方式,保证数据唯一性
		2、class TreeSet
			底层结构为 二叉树结构,要求添加数据必须有自然顺序或者比较顺序的方式
import java.util.HashSet;

/*
 * Set 集合特征演示
 * 	1、存储元素无序
 * 	2、存储元素不可重复
 */
public class Demo1 {
	public static void main(String[] args) {
		/*
		 * Set 是一个接口 
		 * 没有实例化对象 需要使用 Set 集合的实现类 HashSet 类的实例化对象
		 * 
		 * 1、无序
		 * 		数据添加顺序和数据存储顺序不一致
		 * 2、不可重复
		 * 		
		 */
		HashSet<String> set = new HashSet<String>();
		
		set.add("aaa");
		set.add("bbb");
		//添加失败返回 false
		boolean ret = set.add("bbb");
		
		set.add("ccc");
		set.add("ddd");
		set.add("eee");
		set.add("fff");
		set.add("ggg");
		
		System.out.println(ret);
		System.out.println(set);
	}
}

2.2 HashSet 实现类
	底层结构为 哈希表结构,添加元素时需要提供哈希值,所以进行添加元素操作会调用 hashCode()
import java.util.HashSet;

public class Demo2 {
	public static void main(String[] args) {
		HashSet<Person> set = new HashSet<Person>();
		
		/*
		 * 每调用一次添加元素方法 调用一次 hashCode 方法
		 */
		set.add(new Person(1, "甲", 18));
		set.add(new Person(2, "乙", 18));
		set.add(new Person(3, "丙", 18));
		set.add(new Person(4, "丁", 18));
		
		System.out.println();
		
		/*
		 * 执行添加操作 
		 * 要添加的元素按照重写 equals 方法和 hashCode 方法判断是否和集合中已经存在的元素相同
		 * 
		 * 每执行一次添加操作 都会调用 hashCode 方法
		 * 得到该元素对应的哈希值 即添加的元素在集合中对应应该存储位置 
		 * 如果发现该位置已经存在元素 
		 * 调用 equals 方法进行比较 返回值为 true 时表示两个元素相同 无法添加
		 * 返回值为 false 可以添加 避免出现 哈希值相同但 equals 方法返回值不同的情况
		 */
		boolean ret = set.add(new Person(4, "丁", 18));
		System.out.println(ret);
		
		System.out.println("size: " + set.size());
	}
}

2.3 TreeSet 实现类
TreeSet 实现类底层结构为二叉树结构
树状结构要求添加元素必须进行大小比较,即被添加的元素必须有自然顺序或者可比较的方式
2.4 TreeSet 存储自定义元素的方案

【方案一】
自定义类实现 Comparable 接口,变成可比较的类型

/*
 * 实现接口 Comparable 接口泛型约束为 SingleDog 类型
 * 实现接口中的 int CompareTo(SingleDog o) 方法
 * 
 * 可比较的类型
 */
public class SingleDog implements Comparable<SingleDog> {
	private int id;
	private String name;
	private int age;
	
	public SingleDog() {}
	
	public SingleDog(int id, String name, int age) {
		this.id = id;
		this.name = name;
		this.age = age;
	}
	
	public int getId() {
		return id;
	}
	
	public void setId(int id) {
		this.id = id;
	}
	
	public String getName() {
		return name;
	}
	
	public void setName(String name) {
		this.name = name;
	}
	
	public int getAge() {
		return age;
	}
	
	public void setAge(int age) {
		this.age = age;
	}
	
	@Override
	public String toString() {
		return "SingleDog [id=" + id + ", name=" + name + ", age=" + age + "]";
	}
	
	/*
	 * 实现 Comparable接口的 compareTo 方法 返回值类型为 int 类型
	 * 
	 * 返回值可以分为两种情况
	 * 		1、负数或者正数 两个元素存在大小关系 不确定升序还是降序
	 * 		2、0 证明两个元素一致 按照Set 集合特征 无法存储相同元素
	 */
	@Override
	public int compareTo(SingleDog o) {
		//按照年龄进行比较操作
		return age - o.age;
	}
}

import java.util.TreeSet;

public class Demo4 {
	public static void main(String[] args) {
		/*
		 * 实例化 TreeSet对象约束具体数据类型为 自定义类型后
		 * 可以进行排序的方式一:
		 * 自定义类型实现 Comparable<T> 接口 重写接口中的 compareTo 方法
		 */
		TreeSet<SingleDog> set = new TreeSet<SingleDog>();
		
		/*
		 * TreeSet 结构存储的SingleDog 类型 实现了接口 Comparable
		 * 是一个可比较的类型 TreeSet 允许存储
		 * 
		 * TreeSet 接口会自动执行 SingleDog 类实现的 Comparable 接口中的 compareTo 方法
		 * 从而满足当前存储结构排序特征
		 */
		set.add(new SingleDog(1, "甲", 18));
		set.add(new SingleDog(2, "乙", 17));
		set.add(new SingleDog(3, "丙", 16));
		set.add(new SingleDog(4, "丁", 20));
		
		System.out.println(set);
	}
}

【方案二】
TreeSet 插件式增强,提供比较排序存储元素的比较器,比较器实现 Comparator 接口

import java.util.Comparator;
import java.util.TreeSet;

/*
 * 使用 Comparator 接口实现类对象增强 TreeSet
 * 
 * 自定义比较器实现 Comparator 接口 实现接口中的 compare 方法
 * int compare(T o1, T o2);
 */
class PersonComparator implements Comparator<Person> {
	/*
	 * 实现 Comparator 接口的 compare 方法 返回值类型为 int 类型
	 * 
	 * 返回值可以分为两种情况
	 * 		1、负数或者正数 两个元素存在大小关系 不确定升序还是降序
	 * 		2、0 证明两个元素一致 按照 Set 集合特征 无法存储相同元素
	 */
	@Override
	public int compare(Person o1, Person o2) {
		return o1.getAge() - o2.getAge();
	}
}

public class Demo5 {
	public static void main(String[] args) {
		/*
		 * 通过构造方法参数提供自定义 PersonComparator 类的实例化对象
		 * 
		 * Comparator 接口实现类中的 compare 方法由 TreeSet结构自行调整
		 */
		TreeSet<Person> set = new TreeSet<Person>(new PersonComparator());
		
		/*
		 * TreeSet 结构存储的Person 类型 实现了接口 Comparable
		 * 是一个可比较的类型 TreeSet 允许存储
		 * 
		 * TreeSet 接口会自动执行 PersonComparator 比较器实现 Comparator 接口中的 compare 方法
		 * 从而满足当前存储结构排序特征
		 */
		set.add(new Person(1, "甲", 18));
		set.add(new Person(2, "乙", 17));
		set.add(new Person(3, "丙", 16));
		set.add(new Person(4, "丁", 20));
	}
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值