当前位置: 首页 > news >正文

【数据结构】Map与Set

前言

    前两篇文章我们研究了二叉搜索树与哈希表的结构与特点,他们二者是Map与Set这两个接口实现的底层结构,他们利用了搜索树与哈希表查找效率高这一特点,是一种专门用来进行搜索操作的容器或数据结构。本篇文章就让我们一起来梳理这两个接口的特性与用法吧

58d60bbf89ce4be698240c1474f4da73.png

在介绍这两个接口前先说明一下Key-value模型吧:

一般把搜索的数据称为关键字(Key),和关键字对应的称为值(Value),将其称之为Key-value的键值对,所以模型会有两种:
1. key 模型,比如:
有一个英文词典,快速查找一个单词是否在词典中快速查找某个名字在不在通讯录中
2. Key-Value 模型,比如:
统计文件中每个单词出现的次数,统计结果是每个单词都有与其对应的次数:<单词,单词出现的次数>梁山好汉的江湖绰号:每个好汉都有自己的江湖绰号
Map 中存储的就是 key-value 的键值对, Set 中只存储了 Key

一、Map

3784d2b8c38f434db7f6ce60bc674457.png

Map 是一个接口类,该类没有继承自 Collection ,该类中存储的是 <K,V> 结构的键值对,并且 K 一定是唯一的,不 能重复
Map.Entry<K, V> 是 Map 内部实现的用来存放 <key, value> 键值对映射关系的内部类,该内部类中主要提供了<key, value>的获取,value的设置以及Key的比较方式。
注意:Map.Entry<K,V>并没有提供设置Key的方法
Map 的常用方法说明
aad74e44e2cc4ccca5b53e182933d846.png
注意:
1. Map 是一个接口,不能直接实例化对象,如果 要实例化对象只能实例化其实现类 TreeMap 或者 HashMap
2. Map 中存放键值对的 Key 是唯一的, value 是可以重复的
3. 在 TreeMap 中插入键值对时, key 不能为空,否则就会抛 NullPointerException 异常,value可以为空。但是HashMap的key和value都可以为空。
4. Map 中的 Key 可以全部分离出来,存储到 Set 来进行访问(因为Key不能重复)。
5. Map 中的 value 可以全部分离出来,存储在 Collection 的任何一个子集合中(value可能有重复)。
6. Map中键值对的Key不能直接修改,value可以修改,如果要修改key,只能先将该key删除掉,然后再来进行重新插入。
8446713306834a369d27a58cf936962a.png
HashMap的简单实现:
public class HashBuck2<K,V> {static class Node<K,V> {public K key;public V val;public Node<K,V> next;public Node(K key,V val) {this.key = key;this.val = val;}}public Node<K,V>[] array = (Node<K,V>[])new Node[10];//public Node<K,V>[] array = new Node<K,V>[10];public int usedSize;public double loadFactor = 0.75;public void put(K key,V val) {int hash = key.hashCode();int index = hash % array.length;Node<K,V> cur = array[index];//1. 遍历当前链表 是否存在当前值while (cur != null) {if(cur.key.equals(key)) {cur.val = val;return;}cur = cur.next;}//2. 说明 没有当前值,此时进行 头插Node<K,V> node = new Node<K,V>(key,val);node.next = array[index];array[index] = node;usedSize++;}public V get(K key) {int hash = key.hashCode();int index = hash % array.length;Node<K,V> cur = array[index];//1. 遍历当前链表 是否存在当前值while (cur != null) {if(cur.key.equals(key)) {return cur.val;}cur = cur.next;}return null;}
}

TreeMap使用示例:

import java.util.TreeMap;
import java.util.Map;
public static void TestMap(){Map<String, String> m = new TreeMap<>();
// put(key, value):插入key-value的键值对
// 如果key不存在,会将key-value的键值对插入到map中,返回nullm.put("林冲", "豹子头");m.put("鲁智深", "花和尚");m.put("武松", "行者");m.put("宋江", "及时雨");String str = m.put("李逵", "黑旋风");System.out.println(m.size());System.out.println(m);
// put(key,value): 注意key不能为空,但是value可以为空
// key如果为空,会抛出空指针异常
//m.put(null, "花名");str = m.put("无名", null);System.out.println(m.size());
// put(key, value):
// 如果key存在,会使用value替换原来key所对应的value,返回旧valuestr = m.put("李逵", "铁牛");
// get(key): 返回key所对应的value
// 如果key存在,返回key所对应的value
// 如果key不存在,返回nullSystem.out.println(m.get("鲁智深"));System.out.println(m.get("史进"));
//GetOrDefault(): 如果key存在,返回与key所对应的value,如果key不存在,返回一个默认值System.out.println(m.getOrDefault("李逵", "铁牛"));System.out.println(m.getOrDefault("史进", "九纹龙"));System.out.println(m.size());
//containKey(key):检测key是否包含在Map中,时间复杂度:O(logN)
// 按照红黑树的性质来进行查找
// 找到返回true,否则返回falseSystem.out.println(m.containsKey("林冲"));System.out.println(m.containsKey("史进"));
// containValue(value): 检测value是否包含在Map中,时间复杂度: O(N)
// 找到返回true,否则返回falseSystem.out.println(m.containsValue("豹子头"));System.out.println(m.containsValue("九纹龙"));
// 打印所有的key
// keySet是将map中的key防止在Set中返回的for(String s : m.keySet()){System.out.print(s + " ");}System.out.println();
// 打印所有的value
// values()是将map中的value放在collect的一个集合中返回的for(String s : m.values()){System.out.print(s + " ");}System.out.println();
// 打印所有的键值对
// entrySet(): 将Map中的键值对放在Set中返回了for(Map.Entry<String, String> entry : m.entrySet()){System.out.println(entry.getKey() + "--->" + entry.getValue());}System.out.println();
}


二、Set

Set与Map主要的不同有两点:Set是继承自Collection的接口类,Set中只存储了Key。
常见方法说明
36806fd5bfea4a3682513e02124fbb43.png
注意:
1. Set是继承自Collection的一个接口类
2. Set中只存储了key,并且要求key一定要唯一
3. TreeSet的底层是使用Map来实现的,其使用key与Object的一个默认对象作为键值对插入到Map中的
4. Set最大的功能就是对集合中的元素进行去重
5. 实现Set接口的常用类有TreeSet和HashSet,还有一个LinkedHashSet,LinkedHashSet是在HashSet的基础上维护了一个双向链表来记录元素的插入次序。
6. Set中的Key不能修改,如果要修改,先将原来的删除掉,然后再重新插入
7. TreeSet中不能插入null的key,HashSet可以。
7c56d054196046e2b5c58f840606d75b.png
TreeSet使用示例:

import java.util.TreeSet;
import java.util.Iterator;
import java.util.Set;
public static void TestSet(){Set<String> s = new TreeSet<>();// add(key): 如果key不存在,则插入,返回ture// 如果key存在,返回falseboolean isIn = s.add("apple");s.add("orange");s.add("peach");s.add("banana");System.out.println(s.size());System.out.println(s);isIn = s.add("apple");// add(key): key如果是空,抛出空指针异常//s.add(null);// contains(key): 如果key存在,返回true,否则返回falseSystem.out.println(s.contains("apple"));System.out.println(s.contains("watermelen"));// remove(key): key存在,删除成功返回true// key不存在,删除失败返回false// key为空,抛出空指针异常s.remove("apple");System.out.println(s);s.remove("watermelen");System.out.println(s);Iterator<String> it = s.iterator();while(it.hasNext()){System.out.print(it.next() + " ");}System.out.println();
}

总结

    Map与Set这两个接口由于出色的查找效率,为之后的一些算法题中在优化时间上发挥着重要的作用,不过由于创建需要开辟大量空间,是典型的空间换时间,在实际应用中应该根据需要选用。还是哪句话,没有最好的数据结构,只有最适合的数据结构。


那么本篇文章就到此为止了,如果觉得这篇文章对你有帮助的话,可以点一下关注和点赞来支持作者哦。作者还是一个萌新,如果有什么讲的不对的地方欢迎在评论区指出,希望能够和你们一起进步✊

08403404d82e4ca19e76b10b45ca5f28.png

相关文章:

【数据结构】Map与Set

前言 前两篇文章我们研究了二叉搜索树与哈希表的结构与特点&#xff0c;他们二者是Map与Set这两个接口实现的底层结构&#xff0c;他们利用了搜索树与哈希表查找效率高这一特点&#xff0c;是一种专门用来进行搜索操作的容器或数据结构。本篇文章就让我们一起来梳理这两个接口的…...

Flamingo: a Visual Language Model for Few-Shot Learning

发表时间&#xff1a;NeurIPS 2022 论文链接&#xff1a;https://proceedings.neurips.cc/paper_files/paper/2022/file/960a172bc7fbf0177ccccbb411a7d800-Paper-Conference.pdf 作者单位&#xff1a;DeepMind Motivation&#xff1a;仅使用少量注释示例可以快速适应新任务…...

flume性能调优

作者&#xff1a;南墨 1.Source性能调优 1.1 Spooldir Source 使用Spooldir Source采集日志数据时&#xff0c;若每行日志数据<100bp&#xff0c;可以通过将多行合并传输来提升传输性能 建议合并时根据数据长度来确定多少行合并为一个单位进行传输&#xff0c;合并后的长…...

mysql 字符串转数组

在 MySQL 中&#xff0c;可以使用内置的字符串函数 SUBSTRING_INDEX() 和 REPLACE() 来实现将字符串转换为数组。 首先&#xff0c;使用 REPLACE() 函数将字符串中的分隔符替换为空格&#xff0c;然后使用 SUBSTRING_INDEX() 函数将字符串按空格分割成多个子字符串。最后&…...

UE基础 —— 术语

目录 Project Blueprint Class Object Actor Casting Component Pawn Character Player Controller AI Controller Player State Game Mode Game State Brush Volume Level World Project 项目&#xff08;Project&#xff09;包含游戏的所有内容&#xff0c…...

kubernets学习笔记——使用kubeadm构建kubernets集群及排错

使用kubeadm构建kubernets集群 一、准备工作1、repo源配置&#xff1a;阿里巴巴开源镜像源2、更新软件包并安装必要的系统工具3、同步时间4、禁用selinux5、禁用交换分区swap6、关闭防火墙 二、安装docker-ce、docker、cri-docker1、安装docker-ce2、开启内核转发&#xff0c;转…...

简述MYSQL聚簇索引、二级索引、索引下推

一丶聚簇索引 InnoDB的索引分为两种&#xff1a; 聚簇索引&#xff1a;一般创建表时的主键就会被mysql作为聚簇索引&#xff0c;如果没有主键则选择非空唯一索引作为聚簇索引&#xff0c;都没有则隐式创建一个索引作为聚簇索引&#xff1b;辅助索引&#xff1a;也就是非聚簇索…...

电脑开机后出现bootmgr is missing原因及解决方法

最近有网友问我为什么我电脑开机后出现bootmgr is missing&#xff0c;这个提示意思是:意思是启动管理器丢失&#xff0c;说明bootmgr损坏或者丢失&#xff0c;系统无法读取到这个必要的启动信息导致无法启动。原因有很多&#xff0c;比如我们采用的是uefi引导&#xff0c;而第…...

2024 年 7 月公链行业研报:市场波动中 Solana 表现抢眼,Layer 2 竞争白热化

作者&#xff1a;Stella L (stellafootprint.network) 数据来源&#xff1a;Footprint Analytics 公链 Research 页面 7 月份&#xff0c;加密货币市场表现活跃&#xff0c;波动幅度较大&#xff0c;这一现象映射了全球金融市场的整体趋势。现货以太坊 ETP 在美国的上市&…...

Python查缺補漏

一、 json.load(s)与json.dump(s)区别 json.loads()将str类型的数据转换为dict类型 json.dumps()将dict类型的数据转成str json.load()从json文件中读取数据 json.dump()将数据以json的数据类型写入文件中 二、json内部要使用双引号 data """{ "fruit&qu…...

c++的类和对象(中):默认成员函数与运算符重载(重难点!!)

前言 Hello, 小伙伴们&#xff0c;我们今天继续c的学习&#xff0c;我们上期有介绍到c的部分特性&#xff0c;以及一些区别于c语言的地方&#xff0c;今天我们将继续深入了解c的类和对象&#xff0c;探索c的奥秘。 好&#xff0c;废话不多说&#xff0c;开始我们今天的学习。…...

Android .kl按键布局文件

1.介绍 一个硬件按键的处理流程大致为&#xff1a;当用户按下或释放一个键时&#xff0c;键盘硬件会生成一个扫描码scan code&#xff0c;然后操作系统读取这个scan code&#xff0c;并将scan code扫描码映射到虚拟键码key code&#xff0c;最后操作系统根据映射的keycode生成…...

Java每日一练_模拟面试题6(JVM的GC过程)

一、JVM虚拟机组成 JVM五大内存区域&#xff1a;程序计数器&#xff0c;Java虚拟机栈&#xff0c;本地方法栈&#xff0c;java堆&#xff0c;方法区。 堆被划分为两个区域&#xff1a;年轻代(Young)、老年代(Tenured)。年轻代又被划分为三个区域&#xff1a;Eden、From Surviv…...

数据防泄密软件推荐|(6大数据防泄密软件推荐!)

很多朋友在后台私信&#xff0c;什么是数据防泄密软件&#xff0c;有哪些数据防泄密软件推荐。 今天小编将从定义出发&#xff0c;深入浅出地介绍这一技术的工作原理、应用场景以及实现方式。 一、什么是文档透明加密&#xff1f; 文档透明加密是一种在用户无感知的情况下对文…...

Codeforces 874 div3 A-G

A. Musical Puzzle 分析 每两个相邻的字母都要录制一段&#xff0c;开个set记录一下&#xff0c;然后输出set的大小 C代码&#xff1a; #include<iostream> #include<set> using namespace std; void solve(){int n;string s;cin>>n>>s;set<strin…...

暑期数据结构 空间复杂度

3&#xff0e;空间复杂度 空间复杂度也是一个数学表达式&#xff0c;是对一个算法在运行过程中临时占用存储空间大小的量度。 空间复杂度不是程序占用了多少bytes的空间&#xff0c;因为这个也没太大意义&#xff0c;所以空间复杂度算的是变量的个数。空间复杂度计算规则基本跟…...

【Android Studio】图标一键生成 Image Asset Studio(一键各机型适配图标生成工具-告别一个一个替换)

文章目录 方法一&#xff1a;原始替换方法二&#xff1a;Image Asset Studio 方法一&#xff1a;原始替换 https://blog.csdn.net/xzzteach/article/details/140821856 方法二&#xff1a;Image Asset Studio 自动替换所有机型图标...

C++ | Leetcode C++题解之第332题重新安排行程

题目&#xff1a; 题解&#xff1a; class Solution { public:unordered_map<string, priority_queue<string, vector<string>, std::greater<string>>> vec;vector<string> stk;void dfs(const string& curr) {while (vec.count(curr) &am…...

使用Python实现简单的网页爬虫:抓取网站标题

使用Python实现简单的网页爬虫:抓取网站标题 在当今数据驱动的时代,网络爬虫(Web Crawler)成为了获取和分析网络数据的重要工具。无论是数据科学、市场分析还是学术研究,爬虫都能帮助我们从互联网上提取有价值的信息。本文将介绍如何使用Python实现一个简单的爬虫,抓取某…...

视觉SLAM ch3—三维空间的刚体运动

如果对于某些线性代数的知识不太牢固&#xff0c;可以看一下我的另一篇博客&#xff0c;写了一些基础知识并推荐了一些视频。 旋转矩阵 单元所需的线代基础知识https://blog.csdn.net/Johaden/article/details/141023668 一、旋转矩阵 1.点、向量、坐标系 在数学中&…...

Golang 面试经典题:map 的 key 可以是什么类型?哪些不可以?

Golang 面试经典题&#xff1a;map 的 key 可以是什么类型&#xff1f;哪些不可以&#xff1f; 在 Golang 的面试中&#xff0c;map 类型的使用是一个常见的考点&#xff0c;其中对 key 类型的合法性 是一道常被提及的基础却很容易被忽视的问题。本文将带你深入理解 Golang 中…...

跨链模式:多链互操作架构与性能扩展方案

跨链模式&#xff1a;多链互操作架构与性能扩展方案 ——构建下一代区块链互联网的技术基石 一、跨链架构的核心范式演进 1. 分层协议栈&#xff1a;模块化解耦设计 现代跨链系统采用分层协议栈实现灵活扩展&#xff08;H2Cross架构&#xff09;&#xff1a; 适配层&#xf…...

Python爬虫(一):爬虫伪装

一、网站防爬机制概述 在当今互联网环境中&#xff0c;具有一定规模或盈利性质的网站几乎都实施了各种防爬措施。这些措施主要分为两大类&#xff1a; 身份验证机制&#xff1a;直接将未经授权的爬虫阻挡在外反爬技术体系&#xff1a;通过各种技术手段增加爬虫获取数据的难度…...

NLP学习路线图(二十三):长短期记忆网络(LSTM)

在自然语言处理(NLP)领域,我们时刻面临着处理序列数据的核心挑战。无论是理解句子的结构、分析文本的情感,还是实现语言的翻译,都需要模型能够捕捉词语之间依时序产生的复杂依赖关系。传统的神经网络结构在处理这种序列依赖时显得力不从心,而循环神经网络(RNN) 曾被视为…...

用docker来安装部署freeswitch记录

今天刚才测试一个callcenter的项目&#xff0c;所以尝试安装freeswitch 1、使用轩辕镜像 - 中国开发者首选的专业 Docker 镜像加速服务平台 编辑下面/etc/docker/daemon.json文件为 {"registry-mirrors": ["https://docker.xuanyuan.me"] }同时可以进入轩…...

多模态大语言模型arxiv论文略读(108)

CROME: Cross-Modal Adapters for Efficient Multimodal LLM ➡️ 论文标题&#xff1a;CROME: Cross-Modal Adapters for Efficient Multimodal LLM ➡️ 论文作者&#xff1a;Sayna Ebrahimi, Sercan O. Arik, Tejas Nama, Tomas Pfister ➡️ 研究机构: Google Cloud AI Re…...

让回归模型不再被异常值“带跑偏“,MSE和Cauchy损失函数在噪声数据环境下的实战对比

在机器学习的回归分析中&#xff0c;损失函数的选择对模型性能具有决定性影响。均方误差&#xff08;MSE&#xff09;作为经典的损失函数&#xff0c;在处理干净数据时表现优异&#xff0c;但在面对包含异常值的噪声数据时&#xff0c;其对大误差的二次惩罚机制往往导致模型参数…...

Unity UGUI Button事件流程

场景结构 测试代码 public class TestBtn : MonoBehaviour {void Start(){var btn GetComponent<Button>();btn.onClick.AddListener(OnClick);}private void OnClick(){Debug.Log("666");}}当添加事件时 // 实例化一个ButtonClickedEvent的事件 [Formerl…...

针对药品仓库的效期管理问题,如何利用WMS系统“破局”

案例&#xff1a; 某医药分销企业&#xff0c;主要经营各类药品的批发与零售。由于药品的特殊性&#xff0c;效期管理至关重要&#xff0c;但该企业一直面临效期问题的困扰。在未使用WMS系统之前&#xff0c;其药品入库、存储、出库等环节的效期管理主要依赖人工记录与检查。库…...

flow_controllers

关键点&#xff1a; 流控制器类型&#xff1a; 同步&#xff08;Sync&#xff09;&#xff1a;发布操作会阻塞&#xff0c;直到数据被确认发送。异步&#xff08;Async&#xff09;&#xff1a;发布操作非阻塞&#xff0c;数据发送由后台线程处理。纯同步&#xff08;PureSync…...