集合

本文深入解析Java中的Set和Map接口,包括它们的特点、常用方法及实现类如HashSet、HashMap、TreeSet等。同时,介绍了如何使用迭代器遍历集合,以及在实际编程中如何正确重写equals和hashCode方法以实现元素的排重。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、Set接口

4.1Set接口

特点:无序,无下标,不可以重复

4.2常用方法

方法名描述
add(E e)确保此 collection 包含指定的元素(可选操作)。
addAll(Collection<? extends E> c)将指定 collection 中的所有元素都添加到此 collection 中(可选操作)。
clear()移除此 collection 中的所有元素(可选操作)。
contains(Object o)如果此 collection 包含指定的元素,则返回true。
containsAll(Collection<?> c)如果此 collection 包含指定 collection 中的所有元素,则返回 true。
equals(Object o)比较此 collection 与指定对象是否相等。
isEmpty()如果此 collection 不包含元素,则返回true。
iterator()返回在此 collection 的元素上进行迭代的迭代器。
remove(Object o)从此 collection 中移除指定元素的单个实例,如果存在的话(可选操作)。
removeAll(Collection<?> c)移除此 collection 中那些也包含在指定 collection 中的所有元素(可选操作)。
retainAll(Collection<?> c)仅保留此 collection 中那些也包含在指定 collection 的元素(可选操作)。
size()返回此 collection 中的元素数。
toArray()返回包含此 collection 中所有元素的数组。

4.3 Set常用实现类

4.3.1 HashSet

此类实现Set接口,由哈希表支持。它不保证set的迭代顺序;特别是它不保证该顺序恒久不变。此类允许使用null元素。

存储特点:相对无序存储,不可以存储相同元素(排重),通过哈希表实现的集合

4.3.2重写equals()

equals()方法是Object类中的方法,表示比较两个对象是否相等,若不重写相当于比较对象的地址,

为保证元素不重复,必须重写equals()

案例:设计一个Student类,重写equals方法,向一个HashSet集合中添加Student对象,
检验是否排重(若所有属性都相同,视为相同元素)

代码实现:

public class Student {
	private String name;
	private int age;
	@Override
	public String toString() {
		return "Student [name=" + name + ", age=" + age + "]";
	}
	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;
	}
	public Animal() {
		super();
	}
	public Student(String name, int age) {
		super();
		this.name = name;
		this.age = age;
	}
	@Override
  	/*重写equals方法。当添加多个Student对象时,所有属性如果相同,则排重*/
	public boolean equals(Object obj) {
		if(this==obj){
            return ture;
        }
        if(obj==nul)
            return ture;
        if(this.getClass()!=obj.getClass()){
            return false;
        }
        Student s = (Student)obj;

		if(this.name.equals(s.name) && this.age.equals(s.age) && this.sex.equals(s.sex) && 				                       this.score.equals(s.score))
			return true;
			
		return false;
	}
}
4.3.3重写hashCode()

hashCode()是Object中的方法,每个对象的hashCode值是唯一的,所以可以理解成hashCode值表示这个对象在内存中的位置

HashSet集合排重时,需要判断两个对象是否相同,对象相同的判断可以通过hashCode值判断,所以需要重写hashCode()方法

代码实现:

public class Student {
  	private String name;
	private int age;
	@Override
	public String toString() {
		return "Student [name=" + name + ", age=" + age + "]";
	}
	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;
	}
	public Student() {
		super();
	}
	public Student(String name, int age) {
		super();
		this.name = name;
		this.age = age;
	}
	@Override
  	/*重写hashCode()方法,单纯为了检查此方法是否可以实现排重效果,所以返回一个固定的值,使所有本类对象的hashCode值都是相同的*/
	public int hashCode() {
		 return this.name.hashCode() + this.age;
	}
}

同时重写hashCode和equals两个方法,可以实现元素的排重效果

代码实现:

public class Student {
	private String name;
	public Student(String name) {
		super();
		this.name = name;
	}
	public Student() {
		super();
	}
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	@Override
	public String toString() {
		return "Student [name=" + name + "]";
	}
	@Override
  	//重写equals
	public boolean equals(Object obj) {
      	//先判断传入的参数对象是否是Student对象,若不是直接返回false
		if(obj instanceof Student) {
          	//若是,强转成Student对象,并比较属性的值
			Student s = (Student) obj;
			if(this.name.equals(s.name)) {
              	 //若属性的值相同,则返回true
				return true;
			}
		}
		return false;
	}
  	@Override
    public int hashCode(){
      	/*hashCode方法返回值是int类型,所以重写时需要找到int类型的数据返回,还要保证此方法的返回值与对象的所有属性都相关,所以返回姓名属性的hashCode*/
		return this.name.hashCode();
    }
}
4.3.4:TreeSet

基于 TreeMapNavigableSet
实现。使用元素的自然顺序对元素进行排序,或者根据创建 set 时提供的 Comparator
进行排序,具体取决于使用的构造方法。

集合的元素必须实现Comparable接口。

二、Map接口

5.1概念

Map接口是将键(key)映射到值(value)的对象。一个映射不能包含重复的键;每个键最多只能映射到一个值。

无序、无下标、键不可重复,值可重复

常用方法

方法名描述
clear()从此映射中移除所有映射关系(可选操作)。
containsKey(Object key)如果此映射包含指定键的映射关系,则返回 true。
containsValue(Object value)如果此映射将一个或多个键映射到指定值,则返回 true。
equals(Object o)比较指定的对象与此映射是否相等。
get(Object key)返回指定键所映射的值;如果此映射不包含该键的映射关系,则返回 null。
isEmpty()如果此映射未包含键-值映射关系,则返回 true。
keySet()返回此映射中包含的键的 Set 视图。
put(K key, V value)将指定的值与此映射中的指定键关联(可选操作)。
remove(Object key)如果存在一个键的映射关系,则将其从此映射中移除(可选操作)。
size()返回此映射中的键-值映射关系数。
5.1.2 Map实现类 HashMap

基于哈希表的Map接口的实现。此实现提供所有可选的映射操作,并允许使用null值和null键。此类不保证映射的顺序。

存储特点:
相对无序存储,元素以键值对形式存在,键不可以重复,值可以重复,元素整体排重,可以快速的通过键查找到所对应的值,通过哈希表实现的集合。

代码实现

public class TestHashMap {

	public static void main(String[] args) {
		
		HashMap<Integer,String> map = new HashMap<Integer,String>();
		
		map.put(0 , "Hello");
		map.put(1 , "World");
		map.put(2 , "A");
		map.put(3 , "B");
		map.put(4 , "C");
		map.put(5 , "D");
		map.put(6 , "E");
		map.put(0 , "Everyone");
		
		String s = map.remove(1);
		
		for (int i = 0; i < map.size(); i++) {
			if(map.containsKey(i)){
				System.out.println(map.get(i));
			}
		}
		System.out.println("移除的是" + s);
	}

}
存储结构
  1. hashmap底层是以数组方式进行存储。将key-value对作为数组中的一个元素进行存储。
  2. key-value都是Map.Entry中的属性。其中将key的值进行hash之后进行存储,即每一个key都是计算hash值,然后再存储。每一个Hash值对应一个数组下标,数组下标是根据hash值和数组长度计算得来。
  3. 由于不能的key有可能hash值相同,即该位置的数组中的元素出现两个,对于这种情况,hashmap采用链表形式进行存储。
  4. 下图描述了hashmap的存储结构图
  5. 在这里插入图片描述

三、迭代器

6.1什么是迭代器

Java采用了迭代器来为各种容器提供了公共的操作接口。这样使得对容器的遍历操作与其具体的底层实现相隔离,达到解耦的效果。

6.2常用方法

方法名描述
boolean hasNext()如果有元素可以迭代访问,返回true
E next返回迭代的下一个元素

6.3代码实现

public class Demo { 
	public static void main(String[] args) {
		HashMap<String, Integer> map = new HashMap<>();
		map.put("aaa", 111);
		map.put("bbb", 222);
		map.put("ccc", 333);
		//将map转成一个Set集合
		Set<Map.Entry<String, Integer>> set = map.entrySet();
		//遍历set
		Iterator<Map.Entry<String, Integer>> it = set.iterator();
		while(it.hasNext()) {
			System.out.println(it.next());
		}
	}
}

map.put(“aaa”, 111);
map.put(“bbb”, 222);
map.put(“ccc”, 333);
//将map转成一个Set集合
Set<Map.Entry<String, Integer>> set = map.entrySet();
//遍历set
Iterator<Map.Entry<String, Integer>> it = set.iterator();
while(it.hasNext()) {
System.out.println(it.next());
}
}
}


# 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值