三道题教你快速掌握Map和Set

目录

0、简单介绍 Map 和 Set

1、三道关于 Map 和 Set 面试题

第一道题:把这 10W 个数据中的 重复 的元素删除掉

​第二道题:找到这 10W 个数据当中,第一个重复的数据

第三道题:统计这 10W 个数据当中,每个数据出现的次数

2、总结


0、简单介绍 Map 和 Set

Map 和 Set 都是接口类,都不能不能直接实例化对象,如果要实例化只能实例化其对于实现类!

一般情况下,都会使用 HashMap 和 HashSet 进行实例化

Map内部存储的是 键值对 <key,value>,其中 key 不能重复,value可以重复

Set内部存到的是 key,其中 key 不能重复

Map 常用方法如下

方法解释
V get(Object key)返回 key 对应的 value
V getOrDefault(Object key, V defaultValue)返回 key 对应的 value,key 不存在,返回默认值
V put(K key, V value)设置 key 对应的 value
V 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

Set 常用方法如下

方法解释
boolean add(E e)添加元素,但重复元素不会被添加成功
void clear()清空集合
boolean contains(Object o)判断 o 是否在集合中
Iterator<E> iterator()返回迭代器
boolean remove(Object o)删除集合中的 o
int size()返回set中元素的个数
boolean isEmpty()检测set是否为空,空返回true,否则返回false
Object[] toArray()将set中的元素转换为数组返回
boolean containsAll(Collection<?> c)集合c中的元素是否在set中全部存在,是返回true,否则返回
false
boolean addAll(Collection<? extends
E> c)
将集合c中的元素添加到set中,可以达到去重的效果

1、三道关于 Map 和 Set 面试题

现在进行角色扮演,大家现在要去找面试官面试,而我就是大家召唤出来的外挂😁,帮大家指指引迷津

       

 现在面试官给你 10W 个数据,下面你来根据我提问的问题进行操作

public static void func1(int[] array){
     Set<Integer> set = new HashSet<>();
     for (int i = 0; i < array.length; i++) {
         set.add(array[i]);
     }

     System.out.println(set);
}

 Random 类可以产生随机的数据

import java.util.Random;

第一道题:把这 10W 个数据中的 重复 的元素 删除掉

问题记好了吗,记好了我就要睡觉了😂(开玩笑开玩笑) 

这道题我们根据最重要的修饰词是什么?当然是 重复 !! 而当题目中出现 重复 这个关键词时,就相当于告诉我们这道题用 Map 或 Set来解

Map 和 Set最大的特点在于其内部存储的数据不能重复 

为了方便,这道题就用 Set 来解。这道题非常简单,我们只需操心把 10W 个数据全部交给 HashSet,剩下的就 HashSet 帮你解决!!!

    public static void func1(int[] array){
        Set<Integer> set = new HashSet<>();
        for (int i = 0; i < array.length; i++) {
            set.add(array[i]);
        }

        System.out.println(set);
    }

    public static void main(String[] args) {
        int[] array = new int[10_0000];
        Random random = new Random();
        for (int i = 0; i < array.length; i++) {
            array[i] = random.nextInt(5_000);
        }
        func1(array);
    }

 结果如下

 第二道题:找到这 10W 个数据当中,第一个重复的数据

面试官:不错不错,第一道题竟然这么快就解决了,让我来提升一下难度

 看到这道题,我们如果能想到用 Map 和 Set 来解决,就说明我们已经成功 一半了。

为了方便,咱们还用 Set 来解。但是跟第一道不同,我们这次不能一股脑的全部交给 Set 来操作,我们要在存数据的同时判断该数据是由在 Set 中已经出现。

而判断 Set 内部是否包含某个元素我们可以用 contains() 方法,有则返回 true,无则返回 false

    public static int func2(int[] array){
        
        Set<Integer> set = new HashSet<>();
        for (int i = 0; i < array.length; i++) {
            if(set.contains(array[i])){
                return array[i];
            }else{
                set.add(array[i]);
            }
        }
        return -1;
    }
    public static void main(String[] args) {
        int[] array = new int[10_0000];
        Random random = new Random();
        for (int i = 0; i < array.length; i++) {
            array[i] = random.nextInt(5_000);
        }
        System.out.println(func2(array));
    }

第三道题:统计这 10W 个数据当中,每个数据出现的次数

面试官:小伙子不错啊,能走到这一步,看了我要加大难度啦

这道题,我们就不能用 Set 来解决了,因为 Set 只能存储 key值,也就是说 Set 只能简单的去重或者查找第一个重复的元素,而不能记录每个数出现次数。

而 Map 确可以,因为 Map 内部存储的 key-value 键值对,key 和 value 相当于绑定,拿到 key 就能拿到 value

例如 1 1 1 1 2 2  这六个数,放到 Set 内部就变成了 { 1 , 2 }

而放到 Map 中就能变成 { <1,4> , <2,2> },也就是说我们拿到 ‘1’ 就能知道 ‘1’ 出现的次数为四!!! 

思路跟第二题差不多,要边存数据边操作。我们把元素 存到 key 中,而元素出现的次数放到 value 中。

当我们要存一个元素时,先检测它是否在 Map 中存储过,如果没有,就把它放到 Map 中,并把value赋值为1。如果已经存在,那就先获得该元素的 value 值,把 value+1 再放到 Map中。

   public static void func3(int[] array){
        Map<Integer,Integer> map = new HashMap<>();

        for (int i = 0; i < array.length; i++) {
            if(map.containsKey(array[i])){
                int val = map.get(array[i]);
                map.put(array[i],val+1);
            }else{
                map.put(array[i],1);
            }
        }

        System.out.println(map);
    }
    public static void main(String[] args) {
        int[] array = new int[10_0000];
        Random random = new Random();
        for (int i = 0; i < array.length; i++) {
            array[i] = random.nextInt(5_000);
        }
        func3(array);
    }

结果如下: 

面试官:小伙子不错,三道题竟然都解决完了,不错不错,你被录用了😼🎉🎉🎉

突然你一阵眩晕,一睁眼发现原来自己都是自己做的一个梦😅

2、总结

我们通过上述三个题的练习,应该清楚 Map 和 Set 的用法了吧。

我们会发现,一道题能用 Set 解那么就能用 Map来解,而 Map 能解决的 Set 不一定能解决。

如果只是单词的消除重复的元素,那么可以使用 Set。

如果像第三道题那样,每个元素有附加的属性,就如 ‘1’ 出现次数是多少时,用 Map。

 同时,Map 和 Set 内部还可以存储其他类型,或者自定义类,这里我给大家列举一些题目供大家练习掌握

1️⃣只出现一次的数字

2️⃣宝石与石头

3️⃣复制带随机指针的链表

4️⃣旧键盘 (20)

5️⃣前K个高频单词

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱躺平的威威

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值