【Kotlin精简】第2章 集合
1 简介
在 Kotlin 中集合主要分为可变集合
与只读集合
,其中可变集合使用 “Mutable” 前缀 + 集合类名表示,比如 MutableList
、MutableSet
、MutableMap
等。而对于只读集合
就是和 Java 中集合类名是一致。 Java 中的 List 非 Kotlin 中的 List , 因为 Kotlin 中的 List 是只读的而非可变
,却有点类似于 Kotlin 中的 MutableList
。
只读集合
:
内部只具有访问元素的方法,不具有类似 add、remove、clear 之类修改集合的方法。比如 Collection 只读集合内部就没有 add、remove、clear 之类方法,只有 get 访问元素的方法
.可变集合
:
在集合内部既具有访问元素的方法,也具有类似 add、remove、clear 之类修改集合的方法。比如 MutableCollection 可变集合内部就有add
、remove
、clear
之类方法。
集合是可变数量的一组条目。
List
: 是有序集合,可以通过下标访问元素,元素可以重复。
Set
: 是无序集合,有别于List集合的地方在于,1.没有下标,2.元素不允许重复。只能遍历获取参数,遍历参数的顺序与添加顺序相同。元素如果已经存在不进行添加。可以存储Null, 而且Null也是唯一的。
Map
:是无序集合,通过键值对存储数据。每个键唯一。值可以重复。
集合主要就是List
、Set
、Map
,它们在Java中都有接口可以实现,
List --> ArrayList、LinkedList
Set --> HashSet
Map–> HashMap
1.1 List集合
val list = ArrayList<String>()list.add("1")list.add("2")// 创建的是一个不可变的集合,该集合创建成功只能用于读取数据,不能增删改集合数据。val list1 = listOf("aa", "bb")// 创建的是一个可变的集合,可以进行增删改查操作。val list2 = mutableListOf("cc", "dd")// 遍历List集合需要使用for-in循环进行遍历for (content in list1){// 把遍历内容大写content.toUpperCase()print(content) // 输出:aa bb}list2.add("ee")list2.addAll(list1)// 移除指定的元素对象。如果指定元素不存在,移除null。不会报错list2.remove("ee")// 移除参数集合中存在的所有元素。 // 或者,你可以关键字作为参数来调用它;在这种情况下,函数移除关键字匹配true 的所有元素。list2.removeAll(list1)// retainAll() 与 removeAll() 相反,// 它移除除参数集合中的元素之外的所有元素。// 当与关键字一起使用时,它只留下与关键字匹配的元素。list2.retainAll(list)
1.2 Set集合
Set和List的用法其实一样,在初始化时会用到这几个方法:setof()
、mutableSetOf()
// 不可变的集合val set1 = setOf("aa", "bb") // 可变的集合val set2 = mutableSetOf("cc", "dd") // 新增元素set2.add("ee")set2.addAll(set1)// 移除指定的元素对象。如果指定元素不存在,移除null。不会报错set2.remove("ee")// 移除参数集合中存在的所有元素。 // 或者,你可以关键字作为参数来调用它;在这种情况下,函数移除关键字匹配true 的所有元素。set2.removeAll(set1)// retainAll() 与 removeAll() 相反,// 它移除除参数集合中的元素之外的所有元素。// 当与关键字一起使用时,它只留下与关键字匹配的元素。set2.retainAll(set1)
setof()
:创建的是一个不可变的集合,该集合创建成功只能用于读取数据,不能增删改集合数据。
mutableSetOf()
:创建的是一个可变的集合,可以进行增删改查操作。
在这里,Set集合List集合的区别需要注意的是,Set底层是使用Hash映射机制来存储数据的,因此集合中的元素无法保证有序。
----遍历和List一样,就不做解释了
1.3 Map集合
Map集合这里重点介绍,Map和前两者不同,Map是一种键值对形式的数据结构,因此在用法上和List、Set存在很大不同。
一般初始化Map时都需要创建一个HashMap
val map = HashMap<String, String>()
map.put("aa", "1")
map.put("bb", "2")// 因为在Kotlin中,并不建议使用put()、get()方法对Map进行添加和读取数据,
// 而是使用这种类似下标的方式添加数据:
val map1 = HashMap<String, Int>()
map1["aa"] = 1
map1["bb"] = 2// 当读取数据时
val text = map1["aa"]// 移除对应的值,参数为key
map1.remove("aa")
然而,上面这种添加数据方式依然很繁琐,和List、Set一样,Map也有自己的方法mapof()、mutableMapOf()
// 不可变
val map1 = mapOf("aa" to 1, "bb" to 2)
// 可变
val map2 = mutableMapOf("aa" to 1, "bb" to 2)
mapof()
:创建的是一个不可变的集合,该集合创建成功只能用于读取数据,不能增删改集合数据。
mutableMapOf()
:创建的是一个可变的集合,可以进行增删改查操作。
遍历Map集合,也是使用的for-in循环,唯一区别在于,for-in循环中,map键值对变量一起申明到了一对括号中
fun main(){val map1 = mapOf("aa" to 1, "bb" to 2) for ((content1, content2) in map1){print(content1 + "--" + content2)}
}
1.4 集合迭代器 Iterator
提供一种遍历集合元素
的方法,而不暴露集合内部的实现。
1.4.1 迭代器的方式
只要实现了Iterable
接口的类型,都提供迭代器。
下面是使用迭代器的3种方式:
- 使用next()
val numbers = listOf("one", "two", "three", "four")
val numbersIterator = numbers.iterator()
while (numbersIterator.hasNext()) {println(numbersIterator.next())
}
- 使用for…in
val numbers = listOf("one", "two", "three", "four")
for (item in numbers) {println(item)
}
- 使用forEach()
val numbers = listOf("one", "two", "three", "four")
numbers.forEach {println(it)
}
1.4.2 List 的迭代器
List
的迭代器是ListIterator
类型,可以反向迭代:
val numbers = listOf("one", "two", "three", "four")
val listIterator = numbers.listIterator()
while (listIterator.hasNext()) listIterator.next()
println("Iterating backwards:")
while (listIterator.hasPrevious()) {print("Index: ${listIterator.previousIndex()}")println(", value: ${listIterator.previous()}")
}// Iterating backwards:
// Index: 3, value: four
// Index: 2, value: three
// Index: 1, value: two
// Index: 0, value: one
1.4.3 可变迭代器
可变集合(MutableList, MutableSet, MutableMap
)的迭代器都是MutableIterator
类型,可以在迭代的过程中调用remove()
方法删除元素。
val numbers = mutableListOf("one", "two", "three", "four")
val mutableIterator = numbers.iterator()mutableIterator.next()
mutableIterator.remove()println("After removal: $numbers")
// After removal: [two, three, four]
另外,MutableList
的迭代器是MutableListIterator
类型,可以在迭代过程中插入
或替换
元素。
val numbers = mutableListOf("one", "four", "four")
val mutableListIterator = numbers.listIterator()mutableListIterator.next()
mutableListIterator.add("two")
mutableListIterator.next()
mutableListIterator.set("three")println(numbers)
// [one, two, three, four]
1.5 集合Range
使用rangeTo()可以创建范围,rangeTo()对应的操作符:…。
// 遍历范围
for (i in 1..4) print(i)// 反序遍历:
for (i in 4 downTo 1) print(i)// 反序遍历2:
for (i in (1..4).reversed()) print(i)// 定义步长:
for (i in 1..8 step 2) print(i)// 不包含末尾元素:
for (i in 1 until 10) print(i)
1.6 集合序列 Sequence
序列和迭代器的差别
对Iterable
遍历执行多步操作时,会先对所有元素执行一个步骤,将结果保存到中间集合中,然后再对中间集合中所有元素执行下一个步骤,以此类推。相当于,所有元素被并行处理。
对Sequence
遍历执行多步操作时,会对一个元素执行所有步骤,然后再对下一个元素执行所有步骤,以此类推。相当于,所有元素被串行处理。
// 1.通过元素创建
val s1 = sequenceOf(1, 2, 3)// 2.通过Iterable创建
val list = listOf(1,2,3)
val s2 = list.asSequence()// 3.通过generateSequence()函数创建// 4.通过sequence()创建// 例子:假设有很多单词,我们要过滤长度超过3个字母的单词,然后打印前4个这种单词的长度。
// Iterable的方式
val words = "The quick brown fox jumps over the lazy dog".split(" ")
val lengthsList = words.filter { println("filter: $it"); it.length > 3 }.map { println("length: ${it.length}"); it.length }.take(4)
println("Lengths of first 4 words longer than 3 chars:")
println(lengthsList)// Sequence的方式
val words = "The quick brown fox jumps over the lazy dog".split(" ")
// 将 List 转换为序列
val wordsSequence = words.asSequence()
val lengthsSequence = wordsSequence.filter { println("filter: $it"); it.length > 3 }.map { println("length: ${it.length}"); it.length }.take(4)
println("Lengths of first 4 words longer than 3 chars")
// 终止操作: 以 List 形式获取结果
println(lengthsSequence.toList())
filter()
、map()
和take()
这些操作,在调用toList()
后才开始执行。与上面Iterable
相比,是”lazy“的。- 当结果元素数量到达4个时,会停止处理,因为
take(4)
指定了最大元素数量。与上面Iterable
相比,节省了操作步骤。 Sequence
处理执行了 18 步,而使用Iterable
时则需要 23 步。
1.7 常用的集合函数式API
1.7.1 map()函数
它用于将每个元素都映射成一个另外的值,映射规则在Lambda表达式中指定,最终生成一个新的集合,
val list1 = listOf("aa", "bb")
var newList = list1.map{ it.toUpperCase()}
for (content in list1){content.toUpperCase() //转换成大写模式
}
1.7.2 filter()函数
用于过滤集合中的数据,可以单独使用,也可以和map()一起使用
val list1 = listOf("aa", "bbbb", "cc")
var list2 = list1.filter { it.length <= 2 }.map { it.toUpperCase() }
1.7.3 any()函数
判断集合中是否至少存在一个元素满足指定条件
val list1 = listOf("aa", "bbbb", "cc")
var anyResult = list1.any { it.length <= 2 }
1.7.4 all()函数
判断集合中是否所有元素都满足指定条件
val list1 = listOf("aa", "bbbb", "cc")
var allResult = list1.all { it.length <= 2 }
1.7.5 maxBy()函数
定义一个集合,然后找出里面长度最长的元素,maxBy的工作原理是根据传入的条件来进行遍历,从而找打最大值
val list1 = listOf("aa", "bbbb", "cc")
var maxLength = list1.maxBy { it.length }
print(maxLength)
相关文章:

【Kotlin精简】第2章 集合
1 简介 在 Kotlin 中集合主要分为可变集合与只读集合,其中可变集合使用 “Mutable” 前缀 集合类名表示,比如 MutableList、MutableSet、MutableMap 等。而对于只读集合就是和 Java 中集合类名是一致。 Java 中的 List 非 Kotlin 中的 List , 因为 Kot…...

VSCODE+PHP8.2配置踩坑记录
VSCODEPHP8.2配置踩坑记录 – WhiteNights Site 我配置过的最恶心的环境之一:windows上的php。另一个是我centos服务器上的php。 进不了断点 端口配置和xdebug的安装 这个应该是最常见的问题了。从网上下载完php并解压到本地,打开vscode,安装…...

React 状态管理 - Context API 前世今生(下)
New Context API Provider【context的生产者组件】 createContext 创建一个Context对象,订阅了整个Context对象的组件,会从组件树中离自身最近的那个匹配的Provider中读取到当前的context值。Context.Provider 父Context对象返回的Provider组件&#x…...

地下城堡3魂之诗阵容搭配攻略
在地下城堡3魂之诗游戏中,拥有一个合理搭配的阵容非常关键,可以让角色能力发挥最大化。以下是建议的阵容搭配及攻略: 关注【娱乐天梯】,获取内部福利号 1.核心成员(2名) 在阵容中选择两个输出型角色作为核心成员,他们的…...

网工内推 | 技术支持工程师,厂商公司,HCIA即可,有带薪年假
01 华为终端有限公司 招聘岗位:初级技术支持 职责描述: 1、通过远程方式处理华为用户在产品使用过程中各种售后问题; 2、收集并整理消费者声音,提供服务持续优化建议; 3、对服务中发现的热点、难点问题及其他有可能造…...

有 AI,无障碍,AIoT 设备为视障人群提供便利
据世界卫生组织统计,全球共 22 亿人视力受损,包含 2.85 亿视障人群和 3,900 万全盲人群。而且,这一数字将随老龄化加剧不断增加。 虽然视障人群面临着诸多不便,但是针对视障人群的辅助设备却存在成本高、维护困难、操作复杂等问题…...

数据结构学习笔记——数据结构概论
目录 一、数据与数据元素二、数据类型和抽象数据类型三、数据结构的定义(一)逻辑结构(二)存储结构(物理结构)1、顺序存储结构2、链式存储结构3、索引存储结构4、散列存储结构 (三)数…...

关于 打开虚拟机出现“...由VMware产品创建,但该产品与此版VMwareWorkstateion不兼容,因此无法使用” 的解决方法
文为原创文章,转载请注明原文出处 本文章博客地址:https://hpzwl.blog.csdn.net/article/details/133678951 红胖子(红模仿)的博文大全:开发技术集合(包含Qt实用技术、树莓派、三维、OpenCV、OpenGL、ffmpeg、OSG、单片机、软硬结…...

windows的最佳选项卡式窗口管理器软件TidyTabs
下载: https://jmj.cc/s/z1t3kt?pucodeS1wc https://download.csdn.net/download/mo3408/88420433 TidyTabs是一款Windows应用程序,它可以将多个打开的窗口整理成一个选项卡式的界面,使得用户可以更加方便地切换和管理不同的窗口。 Tidy…...

【Python 千题 —— 基础篇】浮点数转为整数
题目描述 题目描述 给出一个浮点数,请将这个浮点数转换成整数。 输入描述 输入一个浮点数。 输出描述 程序将浮点数转换为整数并输出。 示例 示例 ① 2.333输出: 2代码讲解 下面是本题的代码: # 描述: 给出一个浮点数,…...

【Linux--进程间通信】
进程间通信介绍 进程间通信目的 数据传输:一个进程需要将它的数据发送给另一个进程资源共享:多个进程之间共享同样的资源通知事件:一个进程需要向另一个或一组进程发送消息。通知它(它们)发生了某种事件(如…...

Linux C文件操作
文章目录 文件操作函数文件系统调用系统调用与标准函数c的调用的区别文件的读取位置标准c函数系统调用空洞文件 文件的内存映射操作文件目录 linux下的文件操作包括两种,一种是使用C函数,一种是使用系统调用。 gcc 常用来实现c程序的编译gcc filename.c …...

基于Cucumber的行为驱动开发(BDD)实例
本篇介绍 Cucumber 的基本使用, 因为Cucumber是BDD的工具, 所以首先需要弄清楚什么是BDD,而在介绍BDD之前,先看看常见的软件开发方法。 常见的软件开发方法 面向过程开发(Procedural Development)&#x…...

十六、代码校验(2)
本章概要 前置条件 断言(Assertions)Java 断言语法Guava 断言使用断言进行契约式设计检查指令前置条件后置条件不变性放松 DbC 检查或非常严格的 DbCDbC 单元测试 前置条件 前置条件的概念来自于契约式设计(Design By Contract, DbC), 利用断言机制…...

安卓 kotlin-supportFragmentManager报红
如果你继承baseActivity 请查看 是不是继承 AppCompatActivity...

linux中安装RocketMQ以及dashboard
前提: 需要安装jdk8 上传下面的文件到服务器中 新建目录 mkdir rocketmq 将下载后的压缩包上传到阿里云服务器或者虚拟机中去,并解压 unzip rocketmq-all-4.9.2-bin-release.zip 配置环境变量 vim /etc/profile 配置内容: export NAM…...

Android kotlin内联函数(inline)的详解与原理
一、介绍 在kotlin中,有一种函数叫内联函数,这种函数标识符是inline,但是好多人对这个函数的理解只停留在八股文中,内容函数的用法和普通函数没有区别,但是在编译原理上是有,对程序的性能有一定的影响。 二…...

林沛满---一个面试建议
在应聘一个技术职位之前,做好充分的准备无疑能大大提高成功率。这里所说的准备并不是指押题,因为有经验的面试官往往准备了海量的题库,押中的概率太低。比如我有位同事的题库里有上百道题,内容涵盖了编程、操作系统、网络、存储……...

CMake教程-第 5 步:安装和测试
CMake教程-第 5 步:安装和测试 1 CMake教程介绍2 学习步骤Step 1: A Basic Starting PointStep 2: Adding a LibraryStep 3: Adding Usage Requirements for a LibraryStep 4: Adding Generator ExpressionsStep 5: Installing and TestingStep 6: Adding Support f…...

移动应用-Android开发基础\核心知识点
Android开发基础 知识点 1 介绍了解2 系统体系架构3 四大应用组件4 移动操作系统优缺点5 开发工具6 配置工具7 下载相关资源8JDK下载安装流程9配置好SDK和JDK环境10 第一个Hello word11 AS开发前常用设置12模拟器使用运行13 真机调试14 AndroidUI基础布局15 加载展示XML布局16…...

Java读取并转换字符串中的浮点数
在写Android接收蓝牙数据的时候,由于传过来的蓝牙数据转换后都为字符串格式,但是需要从其中提取出来浮点数,所以通过查阅资料写出了从字符串中提取并转换为浮点数的方法,特记录下来以供参考。 目录 原始数据内容 提取字符串中的…...

SQL: 索引原理与创建索引的规范
SQL 索引是一种数据结构,用于加速数据库查询操作。它通过在表的列上创建索引,提供了一种快速查找数据的方法,减少了数据库的扫描和比较操作,从而提高了查询性能。索引根据其实现方式可以分为多种类型,如 B-树索引、哈希…...

基于STM32_DS18B20单总线传感器驱动
基于STM32_DS18B20单总线传感器驱动 文章目录 基于STM32_DS18B20单总线传感器驱动前言一、BS18B20?二、原理1.复位与检验2.基本命令3.唯一ROM识别码4.温度转换 三、驱动代码四、注意事项 前言 本文以一款典型的单总线传感器及其驱动——DS18B20为例,简单…...

目标识别项目实战:基于Yolov7-LPRNet的动态车牌目标识别算法模型(三)
前言 目标识别如今以及迭代了这么多年,普遍受大家认可和欢迎的目标识别框架就是YOLO了。按照官方描述,YOLOv8 是一个 SOTA 模型,它建立在以前 YOLO 版本的成功基础上,并引入了新的功能和改进,以进一步提升性能和灵活性…...

springboot线程池创建与使用
/*** author: zcs* Title: TaskPoolConfig* Description: 线程池配置* date: 2023/10/11 17:52*/ Component public class TaskPoolConfig {Bean(name "threadPoolTaskExecutor")public Executor taskExecutor() {ThreadPoolTaskExecutor taskExecutor new ThreadP…...

UDP和TCP特点(部分)对比:
传输层的两个主要协议:TCP 和 UDP UDP和TCP特点(部分)对比: UDP:无连接, 不可靠传输, 面向数据报, 全双工。 TCP:有连接, 可靠传输, 面向字节流…...

PostMan环境变量、全局变量、动态参数使用
一、环境准备 postmanmoco [{"description": "登录认证","request": {"uri": "/login","method": "post","forms": {"user": "admin","password": "a123…...

服务器数据恢复-服务器硬盘指示灯黄灯闪烁的数据恢复案例
服务器数据恢复环境: 服务器面板上的硬盘指示灯显示黄色是一种警告,提示指示灯对应的服务器硬盘已经被服务器识别出存在故障,硬盘即将下线。如果出现这种情况,建议服务器管理员/运维人员及时用完好的硬盘替换显示黄色指示灯对应的…...

ts 分发
在 TypeScript 中,"分发"(distributive)是指在条件类型中的联合类型上自动进行类型推断的机制。当使用条件类型操作联合类型时,TypeScript 会自动将联合类型中的每个成员都应用该条件类型。 下面是一个示例:…...

SQL中的group by使用注意事项
在 SQL 中,GROUP BY 语句用于将查询结果按照指定的列进行分组,并对每个分组计算聚合函数(如 SUM、AVG、COUNT 等)的值。一般情况下,如果查询中包含聚合函数,那么就需要使用 GROUP BY 语句将查询结果按照指定…...