在数据结构中我们经常会使用到 Map 和 Set ,Map 和 Set 到底是什么,它怎样去使用呢?因此博主整理出 Map 和 Set 这两个接口的介绍与使用方法。
目录
1. 啥是Map和Set?
1.1 Map和Set的模型
2. Map的使用
2.1Map的说明
2.2 Java中Map常用的方法
3. Set的使用
3.1Java中Set的常用方法
1. 啥是Map和Set?
Map 和 Set 是一种专门用来搜索的一个容器或数据结构,它的用途就是为了更快捷、有效的增删改查数据。
在之前的学习中,大家查找数据并对数据进行增删改查基本上使用的都是for循序这种直接遍历的方式,其时间复杂度为O(N),元素如果比较多效率会非常慢。这样的查找是静态的查找。而 Map 和 Set 是实现动态查找的一个集合结构。
通过上图我们可以看到,Set 接口和 Map 接口。底层都有 HashMap 和 TreeMap 使用了这个接口,因此我们把 Map 和 Set 一起来讲。
1.1 Map和Set的模型
通常我们把查找的数据称为关键字 Key,关键字Key对应的值为Value。只有单独的关键字Key我们称为 Key 模型,Key 与 Value 组合的模型我们称之为 键值对。因此有两种解释:
(1)Key模型
Key模型的思想类似于一个快速查询,如在一个数组查找值为Key的元素。Set存储的就是Key模型,其语法格式为:Set<Key>。通过下方程序理解:
public class Test {
public static void main(String[] args) {
Set<Integer> set = new HashSet<>();
set.add(1);//添加Key值为1
set.add(6);//添加Key值为6
System.out.println(set);//输出set集合
}
}
输出:
(2)Key与Value模型
Key与Value,类似于起绰号,如林冲对应的绰号为“豹子头”(Map<林冲,豹子头),罗翔口中的张三对应的绰号为“法外狂徒”(Map<张三,法外狂徒>)。Map中存储的是就是Key-Value的键值对,其语法格式为:Map<Key,Value>。对应下方代码来理解:
public class Test {
public static void main(String[] args) {
Map<Character,Integer> map = new HashMap<>();
map.put('A',6);
map.put('G',3);
System.out.println(map);//输出map集合
}
}
输出:
2. Map的使用
通过上方 Map 和 Set 的模型我们知道了,Map 中存储的是一个<Key,Value>的键值对结构。那么Map 它是一个接口,底层有 HashMap 和 TreeMap 使用了这个接口。
因此,我们不能直接实例化(new)一个Map对象,SortedMap也是一个接口,也不能实例化。但可以实例化 Map 底层的HashMap和TreeMap。因此,我们使用 Map 来操作数据时,使用的就是HashMap 和 TreeMap 了。
2.1Map的说明
在 Map 这个集合中,Map 中 Key 值是唯一的,Value 值可不唯一,借助以下代码来理解:
public static void main(String[] args) {
Map<Character,Integer> map = new HashMap<>();
map.put('A',3);//键值对A,3
map.put('B',3);//键值对B,3
map.put('A',6);//键值对A,6
System.out.println(map);//输出map集合
}
输出:
通过输出结果我们发现到,第一行的键值对A,3没有输出。只输出了第二行键值对 B,3 和第三行的键值对 A,6。因此我们可以确定 Map 集合中Key值 唯一、Value值不唯一。
2.2 Java中Map常用的方法
方法 | 返回类型及参数类型 | 说明 |
---|---|---|
get() | get(Object key) | 返回key对用的value |
getOrDefault() | getOrDefault(Object key, V defaultValue) | 返回key对应的value,key不存在时返回默认值 |
put() | put(K key, V value) | 设置key对应的value |
remove() | remove(Object key) | 删除key对应的映射关系 |
keySet() | Set<K> keySet() | 返回所有key的不重复集合 |
values() | Collection<V> values() | 返回所有的value的可重复集合 |
entrySet() | Set<Map.Entry<K, V>> entrySet() | 返回所有的key,value映射关系 |
containsKey(Object key) | boolean containsKey(Object key) | 判断是否包含key |
containsValue(Object value) | boolean containsValue(Object value) | 判断是否包含value |
以下为这些方法的实例演示:
public static void main(String[] args) {
//实例化一个HashMap对象为map这个集合
Map<Character,Integer> map = new HashMap<>();
//put方法
map.put('A',3);//put方法给map集合添加键值对A,3
map.put('B',3);//put方法给map集合添加键值对B,3
System.out.println("put两个键值对后map集合为: "+map);
System.out.println("输出A对应的value值: "+map.get('A'));//get方法
System.out.println("输出C对应的value值没有则输出默认值666: "+map.getOrDefault('C', 666));
//remove方法
map.remove('A');
System.out.println("删除A后的map集合为: "+map);
//keySet方法
System.out.println("map集合中Key不重复值组成的集合: "+map.keySet());
//entrySet方法
System.out.println("map集合中的所有Key=Value映射(键值对)关系:"+map.entrySet());
//containsKey方法
System.out.println("判断map集合中是否包含Key为A的值: "+map.containsKey('A'));
//containsValue方法
System.out.println("判断map集合中是否包含Value为3的值: "+map.containsValue(3));
}
输出以下内容:
当然,以上的实例是以实例化HashMap的对象来完成的,大家可以尝试使用TreeMap来完成以上方法。
通过上方所有知识点的学习,我们能总结以下几点:
- Map是一个抽象类,不能被实例化,只能实例化底层的HashMap和TreeMap
- Map中存储的键值对Key是唯一的,Value是不唯一的
- Map中的Key可以全部分离出来,存储在Set中的任何一个子集合中(通过Set<K> keySet()方法)。因为Key不能重复!
- Map中的Value也可以全部分离出来,存储在Collection的任何一个子集合中(通过方法Collection<V> values()方法),因为Value可以重复!
- Map中的键值对Key值不能直接修改,Value可修改,如果要修改Key只能先删除Key值再重新插入。
3. Set的使用
通过上方学习,我们知道了Set 与 Map 主要的不同有两点:Set是继承自 Collection 的接口类,Se t中只存储了 Key。
3.1Java中Set的常用方法
方法 | 返回类型及参数类型 | 说明 |
---|---|---|
add() | boolean add(E e) | 添加元素,但重复元素不会被添加成功 |
clear() | void clear() | 清空集合 |
contains() | boolean contains(Object o) | 判断 o 是否在集合中 |
iterator() | Iterator<E> iterator() | 返回迭代器 |
remove() | boolean remove(Object o) | 删除集合中的 o |
size() | int size() | 返回set中元素的个数 |
isEmpty() | boolean isEmpty() | 检测set是否为空,空返回true否则返回false |
toArray() | Object[] toArray() | 将set中的元素转换为数组返回 |
containsAll() | boolean containsAll(Collection<?> c) | 集合c中的元素是否在set中全部存在,是返回true否则返回false |
addAll() | boolean addAll(Collection<? extends E> c) | 将集合c中的元素添加到set中,可以达到去重效果 |
以下为各个方法的实例测试:
public static void main(String[] args) {
Set<Integer> set = new HashSet<>();
set.add(10);//添加元素10
set.add(12);//添加元素12
//打印set集合
System.out.println(set);
//判断11是否在set集合中
System.out.println(set.contains(11));
//返回迭代器
System.out.println(set.iterator());
//删除集合中的10
set.remove(10);
//打印set集合
System.out.println(set);
//输出set集合大小
System.out.println(set.size());
//判断set是否为空,空返回true否则返回false
System.out.println(set.isEmpty());
//将set集合转换为数组的形式
System.out.println(Arrays.toString(set.toArray()));
}
输出:
因此,我们可以总结以下7点:
- Set是继承自Collection的一个接口类
- Set中只存储了key,并且要求key一定要唯一
- Set的底层是使用Map来实现的,其使用key与Object的一个默认对象作为键值对插入到Map中的
- Set最大的功能就是对集合中的元素进行去重
- 实现Set接口的常用类有TreeSet和HashSet,还有一个LinkedHashSet,LinkedHashSet是在HashSet的基础上维护了一个双向链表来记录元素的插入次序。
- Set中的Key不能修改,如果要修改,先将原来的删除掉,然后再重新插入
- Set中不能插入null的key。
当然了,我们掌握了 Map 和 Set 的使用方法后还需要了解的是,在 Map 和 Set 的底层 TreeMap 的结构为红黑树,HashMap 的结构为哈希桶。TreeMap 的查找速度O(log2N),HashMap的查找速度为O(1)。感兴趣的伙伴可以在下方专栏中搜索 TreeMap 和 HashMap 的区别。
🧑💻作者:程序猿爱打拳,Java领域新星创作者,阿里云社区博客专家。
🗃️文章收录于:数据结构与算法
🗂️JavaSE的学习:JavaSE
🗂️MySQL数据库的学习: MySQL数据库
🆕没有对象的朋友赶快给自己new一个对象吧~
本期博文到这里就结束了,如有收获还请关注走一波,感谢您的阅读~