Java[集合] Map 和 Set

简介: Java[集合] Map 和 Set

一、初识 Map 和 Set 集合

首先Map 和 Set 是Java内置的一种专门进行搜索的“容器”同时也是一种数据结构。


我们一般把搜索的数据称之为关键字 (key), 与关键字 key 对应的为值(value),这种模型统称为


“key -value 的键值对”。


Map 采用的是 key - Value 模型,例如:有一个字符串,统计其中每个字符出现的次数,



Set 是 key 模型


什么意思呢,通俗来讲就是只存储出现过的数据且相同数据只存储一个,就是去重,也可以快速判断,某个数据是否存在于Set 集合中。



整体集合框架:



二、如何使用Map

由上图可见,Map 没有继承于 Collection 接口。


Collection接口简介:


Collection抽象的接口,它主要有List和Set两个分支,List和Set也是接口List是一个有序的队列,List中可以有重复的元素;Set中不允许有重复元素存在。

Collection中有一个iterator()函数,它的作用是返回一个Iterator接口。通常,我们通过Iterator迭代器来遍历集合。ListIterator是List接口所特有的,在List接口中,通过ListIterator()返回一个ListIterator对象。

Collection包含了集合的基本操作:添加、删除、清空、遍历、是否为空、获取大小、是否保护某元素等等操作,极大的较少了代码的冗余。

Map 没有继承 Collection 接口,所以关于集合的基本操作Map 有自己的一套逻辑。


Map 是一个接口,不能直接实例化对象,只能是继承Map 接口的 TreeMap,HashMap,这两个实例化对象稍后再着重讲解。


2.1 Map的常用方法

get (Object key)


返回 key 对应的 value


getOrDefault(Object key, V defaultValue)


返回 key 对应的 value,key 不存在,返回默认值


put(K key, V value)


设置 key 对应的 value


remove(Object key)


删除 key 对应的映射关系


Set<K> keySet()


返回所有 key 的不重复集合


Collection<V> values()


返回所有 value 的可重复集合


Set<Map.Entry<K, V>> entrySet()


返回所有的 key-value 映射关系


boolean containsKey(Object key)


判断是否包含 key


boolean containsValue(Object value)


判断是否包含 value


Map中存放键值对的Key是唯一的,value是可以重复的, Map 在添加的过程中,如果遇到相同的Key值,只保留Value 值大的存储,例如: k = a , val = 2, 添加 k = a, val = 3 时, val 值将会被替换为 3


例如:字符串aabcddeb 怎样被Map 集合存储、使用我们将用这个例子给大家演示 Map的常用方法。


public class Test4 {

   public static void main(String[] args) {

       String str = "aabcddeb";

       //使用 Map 统计每个字符出现的次数

       Map<Character,Integer> map = new HashMap<>(); //这里使用 HashMap 来实例化

       for (int i = 0; i < str.length(); i++) { //遍历字符串的元素

           char ch = str.charAt(i);

           if(!map.containsKey(ch)) {//如果字符ch 不存在于map 集合中

               map.put(ch,1); //ch直接存放于集合中

           } else { //如果当前字符存在于集合中

               map.put(ch,map.get(ch) + 1); //使用 put 方法设置 key值对应的val 值

               //get方法是是返回key值对应的 value值 + 1 以此来实现字符个数的偷统计

           }

       }

   }

}


2.1.1 getOrDefault


2.1.2 Set<K> keySet()


Set 集合可以通过Iterator迭代器来遍历集合。


Map 中的Key 可以由键值对分离出来,存储到 Set 集合中,


2.1.3 Collection<V> values()

因为 Map 集合没有继承 Collection 集合,也就没有继承迭代器,所以这是Map 集合自己内置的迭代



Map中的value可以全部分离出来,存储在Collection集合 的任何一个子集合中,例如List, ArrayList……


2.2 Map方法的使用说明

Map.Entry<K, V> 是Map内部实现的用来存放<key, value>键值对映射关系的内部类,该内部类中主要提供了<key, value>的获取,value的设置以及Key的比较方式。


注意:Map.Entry<K,V>并没有提供设置Key的方法,无法单独对 Key 进行修改。


当我们使用Map 集合, 常用方法详解


当我们输入(key, value)键值对,key值不能为空,但是value 可以为空, key 值为空时会抛出空指针异常。


当我们输入(key, value)键值对,如果key 值已经存在, value 值会替代原先 key 值对应的 value 值, put(key,value) 方法返回更新前的 value 值。


get(key) 方法返回 key 对应的 value 值,如果 key 值不存在,返回 null


getOrDefault(Object key, V defaultValue), 返回 key 对应的 value,key 不存在,返回我们设置的默认值,例如 getOrDefault("张三", “学生”),如果map集合中张三不存在,返回我们设置的“学生”。


containKey(key), 判断 key 值是否被包含在 Map 中,时间复杂度:O(logN), 底层是哈希表,哈希。该方法返回 boolean 类型,存在 true,不存在返回 false,


containValue(value),判断 value 是否包含在Map 中,时间复杂度是 O(N),返回值是boolean。


keySet() ,可以将 map 中所有的key 值,放置在 set 集合中,注意: map 返回的 key 值是不重复的,Set 集合的特点也是存储不重复的 value 值。


values() ,可以将map 中所有的 value 值放在 Collect 的任意一个集合中返回,需要迭代。


entrySet() 将Map 中的键值对放在 Set 中返回,什么意思呢,<key , value>作为一个整体放在 Set 集合中,二者之间具有关联性,就不会被单独修改了。


Map 是一个接口,不能直接实例化对象,只能是继承Map 接口的 TreeMap,HashMap,这两个实例化对象,那么 TreeMap 和 HashMap 有什么区别:



HashMap:


基于哈希表实现。使用HashMap要求添加的键类明确定义了hashCode()和equals()[可以重写hashCode()和equals()],为了优化HashMap空间的使用,可以调优初始容量和负载因子。


JDK1.6 后添加了红黑树的逻辑,默认是哈希表的长度达到 8 就转成红黑树,而当长度降到 6 就转换回去哈希表。


TreeMap:


基于红黑树实现。TreeMap没有调优选项,因为该树总处于平衡状态,红黑树的本质就是一棵二叉查找树。


两种常规Map性能


HashMap的底层是Array + 链表的结构,所以HashMap在添加,查找,删除等方法上面速度会非常快,hashmap 集合中的键值对是无序的,录入数据的顺序与 输出的顺序不保证是一样的,例如:录入,“张三”,1 , “李四”,1, 遍历 map 打印的结果可能是先 “李四”,1,“张三”,1 ,因为当 hashmap 扩容时,集合中所有的元素都需要重新哈希!


TreeMap适用于按自然顺序或自定义顺序遍历键(key),底层想象成是一棵有序的二叉树,每插入一个数据或者删除一个数据,TreeMap 就需要重新调整二叉树。


两者各有千秋,在实际运用中按需创建。


Map<Character,Integer> hashMap = new HashMap<>();

Map<Character,Integer> treeMap = new TreeMap<>();

三、如何使用 Set

Set与Map主要的不同有两点:Set是继承自Collection的接口类,Set中只存储了Key。


3.1 Set 的常用方法


3.2 Set 的注意事项

Set是继承自Collection的一个接口类,支持迭代遍历


Set中只存储key 值,并且要求key一定要唯一(不重复),所以我们可以使用 Set 集合来去重


Set中的Key不能修改,如果要修改,先将原来的删除掉,然后再重新插入


Set中不能插入null的key


同一个 Set 集合对象只能存储 同一数据类型


Set 集合也是一个接口,Set的实现主要有以下结构


HashSet集合,底层是HashMap,哈希表+红黑树


TreeSet集合,底层是一个自平衡红黑树,保证元素的顺序


LinkedHashSet集合:底层是哈希表+双向链表组成


Set<Character> hashSet = new HashSet<>();

Set<Character> treeSet = new TreeSet<>();

Set<Character> linkHaSet = new LinkedHashSet<>();

我们经常使用的是 hashSet 和 treeSet, 二者之间的区别,与 Map 集合 的 hashMap 和 treeMap 类似



3.3 Set 常用方法使用说明

add(key) 如果 key 值不存在与 set 集合中,则插入,返回 true, 重复则返回 false, 如果key 值为空,会抛出空指针异常 add(null),。


contains(key) 如果key 存在集合中 ,返回true, 否则返回 false。


remove(key) 如果key 值存在,删除成功返回 true, key 不存在 删除失败返回 false, key 为空抛出空指针异常。


相关文章
|
9天前
|
存储 算法 Java
Java Set深度解析:为何它能成为“无重复”的代名词?
Java的集合框架中,Set接口以其“无重复”特性著称。本文解析了Set的实现原理,包括HashSet和TreeSet的不同数据结构和算法,以及如何通过示例代码实现最佳实践。选择合适的Set实现类和正确实现自定义对象的hashCode()和equals()方法是关键。
21 4
|
9天前
|
Java
那些与Java Set擦肩而过的重复元素,都经历了什么?
在Java的世界里,Set如同一位浪漫而坚定的恋人,只对独一无二的元素情有独钟。重复元素虽屡遭拒绝,但通过反思和成长,最终变得独特,赢得了Set的认可。示例代码展示了这一过程,揭示了成长与独特性的浪漫故事。
16 4
|
9天前
|
Java 开发者
Java Set:当“重复”遇见它,秒变“独宠”!
在Java编程中,Set接口确保集合中的元素不重复,每个元素都是独一无二的“独宠”。本文介绍了Set的两种常见实现:HashSet和TreeSet。HashSet基于哈希表实现,提供高效的添加、删除和查找操作;TreeSet基于红黑树实现,不仅去重还能对元素进行排序。通过示例代码,展示了这两种集合的具体应用,帮助开发者更好地理解和使用Set。
17 4
|
11天前
|
Java
Java 8 引入的 Streams 功能强大,提供了一种简洁高效的处理数据集合的方式
Java 8 引入的 Streams 功能强大,提供了一种简洁高效的处理数据集合的方式。本文介绍了 Streams 的基本概念和使用方法,包括创建 Streams、中间操作和终端操作,并通过多个案例详细解析了过滤、映射、归并、排序、分组和并行处理等操作,帮助读者更好地理解和掌握这一重要特性。
21 2
|
11天前
|
安全 Java
Java多线程集合类
本文介绍了Java中线程安全的问题及解决方案。通过示例代码展示了使用`CopyOnWriteArrayList`、`CopyOnWriteArraySet`和`ConcurrentHashMap`来解决多线程环境下集合操作的线程安全问题。这些类通过不同的机制确保了线程安全,提高了并发性能。
|
14天前
|
存储 Java 开发者
Java Set:无序之美,不重复之魅!
在Java的集合框架中,Set接口以其“无序之美”和“不重复之魅”受到开发者青睐。Set不包含重复元素,不保证元素顺序,通过元素的hashCode()和equals()方法实现唯一性。示例代码展示了如何使用HashSet添加和遍历元素,体现了Set的高效性和简洁性。
28 4
|
14天前
|
存储 算法 Java
为什么Java Set如此“挑剔”,连重复元素都容不下?
在Java的集合框架中,Set是一个独特的接口,它严格要求元素不重复,适用于需要唯一性约束的场景。Set通过内部数据结构(如哈希表或红黑树)和算法(如哈希值和equals()方法)实现这一特性,自动过滤重复元素,简化处理逻辑。示例代码展示了Set如何自动忽略重复元素。
23 1
|
14天前
|
存储 算法 Java
Java中的Set,你真的了解它的“无重复”奥秘吗?
在Java的广阔天地里,Set以其独特的“无重复”特性,在众多数据结构中脱颖而出。本文将揭秘Set的“无重复”奥秘,带你领略其魅力。Set通过哈希算法和equals()方法协同工作,确保元素不重复。通过一个简单的案例,我们将展示HashSet如何实现这一特性。
25 1
|
16天前
|
存储 Java 开发者
在 Java 中,如何遍历一个 Set 集合?
【10月更文挑战第30天】开发者可以根据具体的需求和代码风格选择合适的遍历方式。增强for循环简洁直观,适用于大多数简单的遍历场景;迭代器则更加灵活,可在遍历过程中进行更多复杂的操作;而Lambda表达式和`forEach`方法则提供了一种更简洁的函数式编程风格的遍历方式。
|
15天前
|
存储 Java 开发者
Java中的集合框架深入解析
【10月更文挑战第32天】本文旨在为读者揭开Java集合框架的神秘面纱,通过深入浅出的方式介绍其内部结构与运作机制。我们将从集合框架的设计哲学出发,探讨其如何影响我们的编程实践,并配以代码示例,展示如何在真实场景中应用这些知识。无论你是Java新手还是资深开发者,这篇文章都将为你提供新的视角和实用技巧。
12 0
下一篇
无影云桌面