Scala集合

Scala集合

scala有一组丰富的集合库:List,Tuple,Option,Map

  • 集合可能是严格或懒惰
  • 集合可以是可变的或不可变
  • 不可变的集合可能包含可变项

List

List与Array区别

  • 相同点
    • 所有元素都具有相同的类型
  • 不同点
    • 列表是不可变的,这意味着一个列表的元素可以不被分配来改变.
    • 列表底层是一个链表,而数组是平坦的.

定义Scala的List列表

1.有以下几种常用的方式来定义列表

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// List of Strings
val fruit: List[String] = List("apples", "oranges", "pears")
// List of Integers
val nums: List[Int] = List(1, 2, 3, 4)
// Empty List.
val empty: List[Nothing] = List()
// Two dimensional list
val dim: List[List[Int]] =
List(
List(1, 0, 0),
List(0, 1, 0),
List(0, 0, 1)
)

2.所有的列表可以使用两种基本的构建模块来定义,一个无尾Nil和::,但是这有明显的缺点.Nil也代表了空列表.上述的例子,也可以这样写

1
2
3
4
5
6
7
8
9
10
11
12
13
// List of Strings
val fruit = "apples" :: ("oranges" :: ("pears" :: Nil))
// List of Integers
val nums = 1 :: (2 :: (3 :: (4 :: Nil)))
// Empty List.
val empty = Nil
// Two dimensional list
val dim = (1 :: (0 :: (0 :: Nil))) ::
(0 :: (1 :: (0 :: Nil))) ::
(0 :: (0 :: (1 :: Nil))) :: Nil

::符号就可以简单的替代了List()方法

列表的基本操作

主要针对列表的头尾合是否为空来说

方法 描述
head 此方法返回的列表中的第一个元素
tail 此方法返回一个由除了第一个元素外的所有元素的列表
isEmpty 如果列表为空,此方法返回true,否则为false
1
2
3
4
5
6
7
8
9
10
11
object Test {
def main(args: Array[String]) {
val fruit = "apples" :: ("oranges" :: ("pears" :: Nil))
val nums = Nil
println( "Head of fruit : " + fruit.head )
println( "Tail of fruit : " + fruit.tail )
println( "Check if fruit is empty : " + fruit.isEmpty )
println( "Check if nums is empty : " + nums.isEmpty )
}
}

串联列表

可以使用::运算符或者列表List.:::()方法来添加两个或多个列表

eg:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
object Test {
def main(args: Array[String]) {
val fruit1 = "apples" :: ("oranges" :: ("pears" :: Nil))
val fruit2 = "mangoes" :: ("banana" :: Nil)
// use two or more lists with ::: operator
var fruit = fruit1 ::: fruit2
println( "fruit1 ::: fruit2 : " + fruit )
// use two lists with Set.:::() method
fruit = fruit1.:::(fruit2)
println( "fruit1.:::(fruit2) : " + fruit )
// pass two or more lists as arguments
fruit = List.concat(fruit1, fruit2)
println( "List.concat(fruit1, fruit2) : " + fruit )
}
}

:: 元素之间进行连接,:::列表之间进行连接

创建统一列表

可以使用List.fill()方法来创建,包括相同的元素如下的零个或更多个拷贝的列表

eg

1
2
3
4
5
6
7
8
9
object Test {
def main(args: Array[String]) {
val fruit = List.fill(3)("apples") // Repeats apples three times.
println( "fruit : " + fruit ) //fruit : List(apples, apples, apples)
val num = List.fill(10)(2) // Repeats 2, 10 times.
println( "num : " + num ) //num : List(2, 2, 2, 2, 2, 2, 2, 2, 2, 2)
}
}

反向列表顺序

可以使用List.reverse方法来扭转列表中的所有元素

eg

1
2
3
4
5
6
7
8
9
object Test {
def main(args: Array[String]) {
val fruit = "apples" :: ("oranges" :: ("pears" :: Nil))
println( "Before reverse fruit : " + fruit )
// Before reverse fruit : List(apples, oranges, pears)
println( "After reverse fruit : " + fruit.reverse )
// After reverse fruit : List(pears, oranges, apples)
}
}

Scala列表常用方法

方法 描述
def +(elem: A): List[A] 前置一个元素列表
def ::(x: A): List[A] 在这个列表的开头添加的元素。返回一个新的列表
def :::(prefix: List[A]): List[A] 增加了一个给定列表中该列表前面的元素。返回一个新的列表
def contains(elem: Any): Boolean 测试该列表中是否包含一个给定值作为元素。
def distinct: List[A] 建立从列表中没有任何重复的元素的新列表。
def drop(n: Int): List[A] 返回除了第n个的所有元素。
def endsWithB: Boolean 测试列表是否使用给定序列结束。
…… ……

Set

  • Set集合是不包含重复元素的集合
  • 默认情况下,Scala中使用不可变的集.如果想使用可变集,必须明确导入sala.collection.mutable.Set类

声明Set集合类

1
2
3
4
5
6
7
// Empty set of integer type
var s : Set[Int] = Set()
// Set of integer type
var s : Set[Int] = Set(1,3,5,7)
or
var s = Set(1,3,5,7)

集合基本操作

集合所有操作可以体现在以下三个方法

方法 描述
head 此方法返回集合的第一个元素。

tail|该方法返回集合由除第一个以外的所有元素。|
|isEmpty|如果设置为空,此方法返回true,否则为false。|

eg:

1
2
3
4
5
6
7
8
9
10
11
object Test {
def main(args: Array[String]) {
val fruit = Set("apples", "oranges", "pears")
val nums: Set[Int] = Set()
println( "Head of fruit : " + fruit.head )
println( "Tail of fruit : " + fruit.tail )
println( "Check if fruit is empty : " + fruit.isEmpty )
println( "Check if nums is empty : " + nums.isEmpty )
}
}

串联Set集合

可以使用++运算符或集。++()方法来连接两个或多个集,但同时增加了集它会删除重复的元素

eg

1
2
3
4
5
6
7
8
9
10
11
12
13
14
object Test {
def main(args: Array[String]) {
val fruit1 = Set("apples", "oranges", "pears")
val fruit2 = Set("mangoes", "banana")
// use two or more sets with ++ as operator
var fruit = fruit1 ++ fruit2
println( "fruit1 ++ fruit2 : " + fruit )
// use two sets with ++ as method
fruit = fruit1.++(fruit2)
println( "fruit1.++(fruit2) : " + fruit )
}
}

ScalaSet集合常用方法

方法 描述
def +(elem: A): Set[A] 创建一组新的具有附加元件,除非该元件已经存在
def -(elem: A): Set[A] 创建一个新的从这个集合中删除一个给定的元素
def contains(elem: A): Boolean 如果elem包含在这个集合返回true,否则为false。
def take(n: Int): Set[A] 返回前n个元素
…… ……

Map

  • 在scala中的映射是键/值对的集合即是Map
  • 任何值可以根据它的键进行检索
  • 键是在映射中唯一的,但值不一定是唯一的
  • 映射也被称为哈希表
  • 有两种映射,不可变的以及可变的.不可变的意味着对象本身是不可变的.
  • 默认情况下,scala中使用不可变的映射.要想使用可变集,必须明确导入scala.collection.mutable.Map类

声明Map类

1
2
3
4
5
// Empty hash table whose keys are strings and values are integers:
var A:Map[Char,Int] = Map()
// A map with keys and values.
val colors = Map("red" -> "#FF0000", "azure" -> "#F0FFFF")

映射的基本操作

在映射上的所有操作可被表示在下面的三种方法

方法 描述
keys 这个方法返回一个包含映射中的每个键的迭代。
values 这个方法返回一个包含映射中的每个值的迭代。
isEmpty 如果映射为空此方法返回true,否则为false。

举例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
object Test {
def main(args: Array[String]) {
val colors = Map("red" -> "#FF0000",
"azure" -> "#F0FFFF",
"peru" -> "#CD853F")
val nums: Map[Int, Int] = Map()
println( "Keys in colors : " + colors.keys )
println( "Values in colors : " + colors.values )
println( "Check if colors is empty : " + colors.isEmpty )
println( "Check if nums is empty : " + nums.isEmpty )
}
}

给可变映射添加元素

1
2
3
4
A += ('I' -> 1)
A += ('J' -> 5)
A += ('K' -> 10)
A += ('L' -> 100)

串联映射

可以使用++运算符或映射。++()方法来连接两个或更多的映射,但同时增加了映射,将删除重复的键

eg

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
object Test {
def main(args: Array[String]) {
val colors1 = Map("red" -> "#FF0000",
"azure" -> "#F0FFFF",
"peru" -> "#CD853F")
val colors2 = Map("blue" -> "#0033FF",
"yellow" -> "#FFFF00",
"red" -> "#FF0000")
// use two or more Maps with ++ as operator
var colors = colors1 ++ colors2
println( "colors1 ++ colors2 : " + colors )
// use two maps with ++ as method
colors = colors1.++(colors2)
println( "colors1.++(colors2)) : " + colors )
}
}

遍历Map

方法很多,模式匹配最方便了

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
val colors = Map("red" -> "#FF0000",
"azure" -> "#F0FFFF",
"peru" -> "#CD853F")
println("第一种遍历")
colors.keys.foreach{key=>
print("key= "+key)
println(" value= "+colors(key))}
println("第二种遍历")
for(key <- colors.keySet.toArray) {
println(key+" : "+colors.get(key))
}
println("第三种遍历")
colors.map{
case (k,v)=>println(k+" : "+v)
}

scala中Map的常用方法

方法 描述
def contains(key: A): Boolean 如果有一个绑定在该映射的键返回true,否则为false。
def clone(): Map[A, B] 创建接收器对象的副本
def clear(): Unit 从映射中删除所有绑定。在此之后操作已完成时,映射将是空的。
….. …..

Tuple

Scala的元组结合多个固定数量在一起,使它们可以被传来传去作为一个整体.

特点

  • 不像数组或列表,元组可以容纳不同类型的对象
  • 同时记住,元组也是不可改变的
  • scala目前的元组上限在22个

声明Tuple元组

一个元组的实际类型取决于它包含的元素和这些元素的类型的数目

1
2
3
4
5
6
7
8
9
val t = (1, "hello", Console)
这是语法修饰(快捷方式)以下:
val t = new Tuple3(1, "hello", Console)
//类型:
// (99, "Luftballons") 是 Tuple2[Int, String]
// ('u', 'r', "the", 1, 4, "me") 的类型是 Tuple6[Char, Char, String, Int, Int, String]

访问元组中的元素

1
2
3
4
5
6
7
8
9
object Test {
def main(args: Array[String]) {
val t = (4,3,2,1)
val sum = t._1 + t._2 + t._3 + t._4
println( "Sum of elements: " + sum )
}
}

遍历元组

可以使用Tuple.productIterator()方法来遍历一个元组的所有元素

1
2
3
4
5
6
object Test {
def main(args: Array[String]) {
val t = (4,3,2,1)
t.productIterator.foreach{ i =>println("Value = " + i )}
}
}

元组的简单方法

1.转换为字符串
2.交换元素

1
2
3
4
5
6
7
8
9
10
object Test {
def main(args: Array[String]) {
val t1 = new Tuple3(1, "hello", Console)
println("Concatenated String: " + t1.toString() )
val t2 = new Tuple2("Scala", "hello")
println("Swapped Tuple: " + t2.swap )
}
}
Donate comment here