Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >专栏 >Scala中的Collection

Scala中的Collection

作者头像
ZONGLYN
发布于 2019-08-08 02:53:33
发布于 2019-08-08 02:53:33
1.2K00
代码可运行
举报
文章被收录于专栏:程序萌部落程序萌部落
运行总次数:0
代码可运行

Scala中的immutable Collection 集合

Traversable 遍历 Iterable 迭代 Set无序集合 Sequence序列 Map映射

  • Set
  • SortedSet HashSet BitSet ListSet
  • TreeSet
  • Sequence
  • IndexedSeq LinearSeq
  • IndexedSeq
  • Vector,NumericRange,Range,Array,String
  • LinearSeq
  • List,Stream,Quene,Stack
  • Map
  • Sortedmap HashMap LsitMap
  • TreeMap

List[T]

T是类型,由于会自动推导类型,所以不必指明类型

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
scala> val a = List(1,2,3,4)        //定义方法一
a: List[Int] = List(1, 2, 3, 4)     //自动推导为Int类型的List
scala> val b = 0::a                 //定义方法二:连接操作符
b: List[Int] = List(0, 1, 2, 3, 4)  //将左边的元素添加到右边List的头部
scala> var c = "x"::"y"::"z"::Nil   //Nil是空List
c: List[String] = List(x, y, z)     
//上述过程是从右往左连接,步骤如下:
scala> "z"::Nil
res5: List[String] = List(z)
scala> "y"::res5
res6: List[String] = List(y, z)
scala> "x"::res6
res7: List[String] = List(x, y, z)
scala> val d = a:::c                //定义方法三:使用:::连接两个List
d: List[Any] = List(1, 2, 3, 4, x, y, z)
                                    //自动推导为Int,String的父类为Any
scala> a.head
res8: Int = 1
scala> d.head                       //.head返回头元素
res9: Any = 1
scala> c.head
res10: String = x
scala> a.tail                       //.tail返回除头元素之外的元素
res11: List[Int] = List(2, 3, 4)
scala> d.tail
res12: List[Any] = List(2, 3, 4, x, y, z)
scala> a.isEmpty                    //.isEmpty返回List是否为空
res13: Boolean = false
scala> Nil.isEmpty
res14: Boolean = true
//利用tail和isEmpty构造循环来实现List的遍历:
scala> def scanf(list: List[Int]):String = {
     | if(list.isEmpty) "NULL"
     | else list.head.toString+" "+scanf(list.tail)
     | }
scanf: (list: List[Int])String
scala> scanf(a)
res15: String = 1 2 3 4 NULL

List的高阶函数 filter:过滤

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//将List元素进行过滤
//下面filter参数是一个匿名函数,x代表一个元素,filter会遍历List判断每个元素是否满足条件
scala> a.filter(x => x % 2 ==1) 
res17: List[Int] = List(1, 3)
//toList表达式,结果是将当前字符串转为List
scala> "100 Persons".toList
res18: List[Char] = List(1, 0, 0,  , P, e, r, s, o, n, s)
//判断是否为数字可以用Character.isDigit(x)方法
scala> "100 Persons".toList.filter(x => Character.isDigit(x))
res20: List[Char] = List(1, 0, 0)
//takeWhile满足条件则取元素,直到!取到某元素才停止
//(类似while循环)下面取元素取到字符‘o’终止,并且不会打印‘o’
scala> "100 Persons".toList.takeWhile(x => x!='o')
res21: List[Char] = List(1, 0, 0,  , P, e, r, s)

List的高阶函数 map/flatMap:映射

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//对于下面的变量a和c应用映射
scala> a
res22: List[Int] = List(1, 2, 3, 4)
scala> c
res22: List[String] = List(x, y, z)
//map的参数就是一个匿名函数,表明一个转换过程,参数中的匿名函数参数x是List中得每个元素
//使用map实现全部字母大写
scala> c.map(x => x.toUpperCase)
res23: List[String] = List(X, Y, Z)
//参数中的匿名函数参数x可以使用通配符下划线'_'来代替
scala> c.map( _.toUpperCase)
res24: List[String] = List(X, Y, Z)
//同样的filter也可以使用通配符下划线'_'来代替
scala> a.filter( _ % 2 ==1)
res25: List[Int] = List(1, 3)
//通过filter和map来实现对List中过滤后元素的具体操作
//下面是将奇数全部加10
scala> a.filter( _ % 2 ==1).map( _ +  10)
res26: List[Int] = List(11, 13)
//下面是嵌套List
scala> val complex = List( a,List(4,5,6))
complex: List[List[Int]] = List(List(1, 2, 3, 4), List(4, 5, 6))
//对于嵌套List,filter仍然会遍历到最里层的元素并且进行过滤
//但是其返回不会去掉外壳,仍然是个嵌套List
scala> complex.map(x => x.filter( _%2 ==0))
res27: List[List[Int]] = List(List(2, 4), List(4, 6))
//同样,使用下划线也可以通配参数x
scala> complex.map( _.filter( _%2 ==0))
res28: List[List[Int]] = List(List(2, 4), List(4, 6))
//使用flatMap可以将嵌套List“打平”,将返回元素全部放在同一层
//下面就可以取出嵌套List中的偶数,注意,去除了‘外壳’
scala> complex.flatMap( _.filter( _%2 ==0))
res30: List[Int] = List(2, 4, 4, 6)

List的高阶函数 集合的规约操作

把集合的元素通过运算和操作规约为一个值

reduceLeft(op: (T, T) => T )

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
x1  x2  x3      ... xn
  op    x3      ... xn
     op         ... xn
                ...
                 op

特性1:参数为一个匿名函数 特性2:规约结果一定是List元素的类型,所以是被经常使用的(相较于foldLeft)

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
对于List变量a
scala> a
res33: List[Int] = List(1, 2, 3, 4)
使用reduceLeft,参数为匿名函数,表示规约的表达式
scala> a.reduceLeft((x,y) => x+y)
res31: Int = 10
可以使用下划线通配
scala> a.reduceLeft(_+_)
res32: Int = 10

foldLeft(z:U)(op: (U, T) => U )

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
z   x1  x2      ... xn
  op    x1      ... xn
     op         ... xn
                ...
                 op

特性1:使用柯里化定义 特性2:必须有初始值z 特性3:返回值是初始值z的类型,故不太使用

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
scala> a
res33: List[Int] = List(1, 2, 3, 4)
//使用foldLeft进行元素的求和,并且初值为0
scala> a.foldLeft(0)((x,y) => x+y)
res34: Int = 10
//使用通配符
scala> a.foldLeft(0)(_+_)
res35: Int = 10
//初值改变后的结果
scala> a.foldLeft(1)(_+_)
res36: Int = 11

惰性求值的类型:Stream 流

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//使用to或until来获取range类型
scala> 1 to 10 by 2
res41: scala.collection.immutable.Range = inexact Range 1 to 10 by 2
//until是小于,取不到边界
scala> (1 until 10).toList
res44: List[Int] = List(1, 2, 3, 4, 5, 6, 7, 8, 9)
//to是小于等于,可以取边界
scala> (1 to 10).toList
res45: List[Int] = List(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
//使用操作符#::来连接定义一个Stream,其中Stream.empty是空流
scala> 1 #:: 2#:: 3#:: Stream.empty
res46: scala.collection.immutable.Stream[Int] = Stream(1, ?)
//惰性求值的特性:由打印可知,只显示和判断第一个元素是什么,其他的用?表示
scala> val s = (1 to 1000).toStream
s: scala.collection.immutable.Stream[Int] = Stream(1, ?)
//获取Stream的第一个元素
scala> s.head
res48: Int = 1
//获取Stream除首元素以外的元素,其返回结果仍然是Stream类型,所以仍然只显示(2, ?)
scala> s.tail
res49: scala.collection.immutable.Stream[Int] = Stream(2, ?)
scala> s.tail.head
res50: Int = 2

Scala中的tuple:元组

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//元组的概念,和Python中的元组类似,可以放不用类型的变量
scala> (1,2)
res51: (Int, Int) = (1,2)
//只有两个元素的元组叫pair,可以使用箭头的方式来定义
scala> 1 -> 2
res52: (Int, Int) = (1,2)
//scala自动识别元素类型
scala> val t = (1,'a',"Tom",34.5)
t: (Int, Char, String, Double) = (1,a,Tom,34.5)
//对于一个元组变量,下划线加数字表示第N个元素,t._1表示第一个元素
scala> t._1
res54: Int = 1
//取元素时不能超出下标,否则报错
scala> t._5
<console>:13: error: value _5 is not a member of (Int, Char, String, Double)
       t._5
         ^

元组的用处: 可以封装函数的返回值,在函数返回多个类型的变量时,可以包装起来一并返回

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//下面这个函数通过元组,一并返回输入参数List变量中所有元素的个数、求和、平方和
scala> def _3operate(in:List[Int]):(Int,Int,Int) =
     | in.foldLeft((0,0,0))((t,v) => (t._1+1,t._2+v,t._3+v*v)
     | )
_3operate: (in: List[Int])(Int, Int, Int)
//调用该函数,可以返回三个值
scala> _3operate(a)
res56: (Int, Int, Int) = (4,10,30)

Scala中的Map

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//使用类似元组的箭头来定义一个键值对
scala> val p = Map(1 ->  "Tom",9->"Jack")
p: scala.collection.immutable.Map[Int,String] = Map(1 -> Tom, 9 -> Jack)
//按Key取值
scala> p(1)
res58: String = Tom
//判断指定Key是否在Map中
scala> p.contains(1)
res59: Boolean = true
//返回包含全部Key的Set集合
scala> p.keys
res60: Iterable[Int] = Set(1, 9)
//返回包含全部Value的Iterable类型
scala> p.values
res61: Iterable[String] = MapLike.DefaultValuesIterable(Tom, Jack)
涉及的Map相关运算

涉及的Map相关运算

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//使用+号 添加键值对,注意Map不支持混合类型的添加,否则会出错
scala> p + ("name" -> "Kim")
<console>:13: error: type mismatch;
 found   : (String, String)
 required: (Int, ?)
       p + ("name" -> "Kim")
                   ^
//正确添加键值对,注意会按Key值覆写键值对,即Key冲突时丢弃原来的Value
//有冲突的添加
scala> p + (1 -> "Kim")
res63: scala.collection.immutable.Map[Int,String] = Map(1 -> Kim, 9 -> Jack)
//正常的添加
scala> p + (2 -> "Kim")
res65: scala.collection.immutable.Map[Int,String] = Map(1 -> Tom, 9 -> Jack, 2 -> Kim)
//使用-号来删除键值对,注意减的是Key值
scala> p - 1
res70: scala.collection.immutable.Map[Int,String] = Map(9 -> Jack)
//注意添加或删减的结果不能直接通过= 赋值给自己,会报错
scala> p = p -9
<console>:12: error: reassignment to val
       p = p -9
         ^
//上述的添加和删除都是操作单个元素,下面使用包含键值对的List集合加上++运算符来完成添加拖个键值对
scala> p ++ List(2->"a",5->"b")
res72: scala.collection.immutable.Map[Int,String] = Map(1 -> Tom, 9 -> Jack, 2 -> a, 5 -> b)
//删除多个键值对,注意删除只需要含Key值的List即可
scala> p -- List(1,9,2,5)
res73: scala.collection.immutable.Map[Int,String] = Map()
//可以联合构成表达式
scala> p ++ List(2->"a",5->"b") -- List(2,5)
res74: scala.collection.immutable.Map[Int,String] = Map(1 -> Tom, 9 -> Jack)

函数式编程示例:快速排序

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def qSort(a:List[Int]):List[Int] = {
		if(a.length < 2) a
		else
			qSort( a.filter( _ < a.head )) ++ 
			a.filter( _ == a.head ) ++ 
			qSort( a.filter( _ > a.head ))
			
}                                 //> qSort: (a: List[Int])List[Int]
qSort(List(2,3,5,1,2,8,5,2))      //> res0: List[Int] = List(1, 2, 2, 2, 3, 5, 5, 8)
qSort(List(9,4,8,2,5,1,3,0))      //> res1: List[Int] = List(0, 1, 2, 3, 4, 5, 8, 9)

解释:

首先快排需要一个分割变量,这里直接用a.head即输入List的第一个元素来做分割 其次是归类,每次递归都要分出小于,大于和等于的元素 然后是合并,使用++操作符,把每次的元素拼接起来,即每次调整后的结果 最后是判断递归结束条件:如果当前作为输入的分割后的List元素不足2,那么表示无序调整,排序结束

注意:

这里外层递归中含有两个递归,外层递归即函数的返回的是三部分之和,这并不是尾递归 这个例子是综合了函数式编程、高阶函数、递归等Scala编程思想的体现。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2017-10-30,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
编辑精选文章
换一批
Scala学习一
1.集合操作练习 //创建一个List val lst0 = List(1,7,9,8,0,3,5,4,6,2) //将lst0中每个元素乘以10后生成一个新的集合 lst0.map(x => x*10 ) OR lst0.map(_*10 ) //将lst0中的偶数取出来生成一个新的集合 lst0.filter(x => x%2==0) lst0.filter(x => x%2==0).map(_*5) //将lst0排序后生成一个新的集合 lst0.sorted lst0.sortBy(x => x
sparkle123
2018/04/28
1.2K0
Scala Collection简介
Traversable vs Iterable Traversable, Iterable 都是trait。 Iterable 继承 Traversable。 Traversable: 支持foreach. Iterable: 支持Interator方法。 Immutable vs mutable Scala的Collection有Immutable和mutable两个大家族。 Immutable: 不可变。初始化后不会发生变化。scala的默认collections。性能更好。 Mutable:
绿巨人
2018/05/16
9160
Spark基础-scala学习(一、入门)
Scala解析器的使用 REPL:Read(取值)-> Evaluation(求值)-> Print(打印)->Loop(循环)。scala解析器也被称为REPL,会快速编译scala代码为字节码,然后交给JVM执行 val result = 1 设置变量不可变 var result = 2 可变的变量 val name: String = null 声明变量类型 val name: Any = "leo" val name1,name2:String = null 声明多个变量 val num1,num2
老梁
2019/09/10
7350
Scala学习笔记
大数据框架(处理海量数据/处理实时流式数据) 一:以hadoop2.X为体系的海量数据处理框架         离线数据分析,往往分析的是N+1的数据         - Mapreduce             并行计算,分而治之             - HDFS(分布式存储数据)             - Yarn(分布式资源管理和任务调度)             缺点:                 磁盘,依赖性太高(io)                 shuffle过程,map将数据写入到本次磁盘,reduce通过网络的方式将map task任务产生到HDFS         - Hive 数据仓库的工具             底层调用Mapreduce             impala         - Sqoop             桥梁:RDBMS(关系型数据库)- > HDFS/Hive                   HDFS/Hive -> RDBMS(关系型数据库)         - HBASE             列式Nosql数据库,大数据的分布式数据库  二:以Storm为体系的实时流式处理框架         Jstorm(Java编写)         实时数据分析 -》进行实时分析         应用场景:             电商平台: 双11大屏             实时交通监控             导航系统  三:以Spark为体系的数据处理框架         基于内存            将数据的中间结果放入到内存中(2014年递交给Apache,国内四年时间发展的非常好)         核心编程:             Spark Core:RDD(弹性分布式数据集),类似于Mapreduce             Spark SQL:Hive             Spark Streaming:Storm         高级编程:             机器学习、深度学习、人工智能             SparkGraphx             SparkMLlib             Spark on R Flink
曼路
2018/10/18
2.6K0
Scala中的集合类型
----------目录--------------------------------------------------------- 1.Scala简介和安装 2.Scala语法介绍 3.Scala的函数 4.Scala中的集合类型 ------------------------------------------------------------------------------------------------------------- Scala中的集合类型     Scala提供了一套
云飞扬
2018/05/11
4.3K0
Scala | 教程 | 学习手册 --- 常用集合
所有集合的根是Iterator,它提供了一组公共方法,可以用来迭代处理和管理集合数据。
曲奇
2021/12/14
5970
Scala | 教程 | 学习手册 --- 常用集合
Scala入门篇 顶
scala> val a = println("ddd") ddd a: Unit = ()
算法之名
2019/08/21
4800
Scala入门篇
                                                                            顶
Scala 学习笔记之Map与Tuple
上面构造了一个不可变的Map[String, Int],其值也不能被改变.如果想要一个可变映射,使用如下命令创建:
smartsi
2019/08/07
6440
Scala 集合
Option 是一个表示有可能包含值的容器。 Option 本身是泛型的,并且有两个子类: Some[T] 或 None
Freedom123
2024/03/29
890
01.Scala:开发环境搭建、变量、判断、循环、函数、集合
早期,scala刚出现的时候,并没有怎么引起重视,随着Kafka和Spark这样基于scala的大数据框架的兴起,scala逐步进入大数据开发者的眼帘。scala的主要优势是它的表达性。
Maynor
2021/04/09
4.2K0
Scala的函数
----------目录--------------------------------------------------------- 1.Scala简介和安装 2.Scala语法介绍 3.Scala的函数 4.Scala中的集合类型 ------------------------------------------------------------------------------------------------------------- Scala的函数 1、函数的声明     scala
云飞扬
2018/05/11
1.4K0
Scala学习笔记(八)
模式匹配是 Scala 的重要特性之一,前面两篇笔记Scala学习笔记(六) Scala的偏函数和偏应用函数、Scala学习笔记(七) Sealed Class 和 Enumeration都是为了这一篇而铺垫准备的。
fengzhizi715
2018/08/24
1.1K0
Scalaz(8)- typeclass:Monoid and Foldable
该文章介绍了如何使用Monoid类型进行并行计算和并行序列化。首先介绍了Monoid的概念,以及如何使用Scalaz库中的Monoid类型进行并行计算。然后介绍了如何使用Monoid类型进行并行序列化,并提供了几个例子。最后还介绍了如何使用Monoid类型进行并行处理,并提供了几个例子。
用户1150956
2018/01/05
1.1K0
scala 容器详细解释
scala 中的所有集合类位于 scala.collection 或 scala.collection.mutable,scala.collection.immutable,scala.collection.generic 中
Tim在路上
2020/08/04
1.3K0
大数据利器--Scala语言学习(高级)
ListBuffer:ListBuffer 是可变的 list 集合,可以添加,删除元素,ListBuffer 属于序
MiChong
2020/09/24
2K0
大数据利器--Scala语言学习(高级)
学好Spark必须要掌握的Scala技术点
Scala是以JVM为运行环境的面向对象的函数式编程语言,它可以直接访问Java类库并且与Java框架进行交互操作。
大数据学习与分享
2020/08/10
1.7K0
学好Spark必须要掌握的Scala技术点
Scalaz(24)- 泛函数据结构: Tree-数据游览及维护
上节我们讨论了Zipper-串形不可变集合(immutable sequential collection)游标,在串形集合中左右游走及元素维护操作。这篇我们谈谈Tree。在电子商务应用中对于xm
用户1150956
2018/01/05
7360
泛函编程(7)-数据结构-List-折叠算法
     折叠算法是List的典型算法。通过折叠算法可以实现众多函数组合(function composition)。所以折叠算法也是泛函编程里的基本组件(function combinator)。了
用户1150956
2018/01/04
7960
泛函编程(7)-数据结构-List-折叠算法
有趣的Scala列表
其中Nil表示空列表,::符号表示在列表前面追加元素,所以如果没有后面的Nil,Scala就会报错。
哒呵呵
2018/08/06
5340
如何在 Scala 中科学地操作 collection(一)集合类型与操作
在日常项目开发中,我们几乎都会用到Scala中的集合以及一些集合操作。由于 Scala 中的集合操作灵活多变,对于刚接触Scala的开发者,在选用何种集合以及使用何种集合操作就显得不那么合理了,虽然大
Albert陈凯
2018/04/04
1.2K0
如何在 Scala 中科学地操作 collection(一)集合类型与操作
相关推荐
Scala学习一
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验