if条件
除了和 Java 相同的 if... else if ... else语句功能外,Scala中的if代码块可以有返回值,即代码块最后一行会被当做返回值:
val a: Int = 10// 可以用变量接收if的返回值val result: Int =if (a < 1) {a + 1 // 代码块中的最后一句代码就是返回值} else if (a < 10) {a + 10} else if (a > 100) {a} else {100}println(result)
for循环
语法:
for( var x <- Range ){statement(s);}
:::info
以上语法中,Range 可以是一个数字区间表示 i to j (包含j),或者 i until j (不包含 j)。左箭头 <- 用于为变量 x 赋值。
注意:i >= j ,例如1 to 10, 不可 i < j
:::
i to j 语法(包含 j)
object Test {def main(args: Array[String]) {var a = 0;// for 循环for( a <- 1 to 10){println( "Value of a: " + a );}}}
i until j 语法(不包含 j)
object Test {def main(args: Array[String]) {var a = 0;// for 循环for( a <- 1 until 10){println( "Value of a: " + a );}}}
循环嵌套
Scala支持像 Java 一样的循环嵌套,另外,还可以将嵌套的循环写到一行中:
可以使用分号 (;) 来设置多个区间(嵌套for循环)
object Test {def main(args: Array[String]) {var a = 0;var b = 0;// for 循环for (a <- 1 to 3; b <- 1 to 3) {println("Value of a: " + a + "b:" + b);}}}输出结果:Value of a: 1 b: 1Value of a: 1 b: 2Value of a: 1 b: 3Value of a: 2 b: 1Value of a: 2 b: 2Value of a: 2 b: 3Value of a: 3 b: 1Value of a: 3 b: 2Value of a: 3 b: 3
集合的嵌套循环:
val list = List(List(1, 2, 3), List(4, 5, 6), List(7, 8, 9)) // List内部元素还是List// 遍历for (subList <- list; elem <- subList) {println(elem)}输出结果:123456789
设置步长和倒序
to、until方法指定步长:
:::info
步长的意思类似 i++,by 2 就是每次 + 2
:::
// 0.to(10)得到一个Range对象,然后调用Range对象的by方法指定步长// 指定步长为2for(i <- 0 to 10 by 2) {println(i)}// 步长还可以定义为负值:当起始值大于结束值时,将步长定义为负值,则可以倒序遍历。//(如果起始值小于结束值,步长定义为负值,那么Scala认为是死循环,就直接跳过不运行这个循环)// 但是步长不可以设置为0for(i <- 10 until 0 by -2) {println(i)}// 也可以通过调用Range的reverse方法实现反转倒序遍历for(i <- 0 to 10 by 2 reverse) {println(i)}
集合元素遍历
对于数组、集合的元素,也可以直接进行遍历:
// 遍历数组的元素for (i <- Array(11, 24, 51, 13, 33)) {println(i)}// 遍历集合的元素for (i <- List(11, 24, 51, 13, 33)) {println(i)}
循环守卫
Scala的循环语句中,可以加入条件判断(即循环保护式,循环守卫),当条件判断为true时才执行,为false时则直接continue(Scala中没有continue关键字)。
例如:
// 遍历1到5中的所有偶数for (i <- 1 to 5 if i%2 == 0) { // 直接以循环守卫的方式加入判断语句:if i%2 == 0println(i)}
引入变量
示例:
val list = List(10,11,12,13,14,15)// 在循环表达式中,可以新建一个变量,即使这个变量不是嵌套循环for (i <- 0 to 5 ; j = list(i)) {println(j)}
循环的返回值
通过yield关键字声明循环要返回的内容:
// 此处的 yield 和线程无关,只是声明要返回的内容// 返回的是一个Vector集合val forResult = for (i <- 1 to 10) yield (i * 2) ;println(forResult)输出结果:Vector(2, 4, 6, 8, 10, 12, 14, 16, 18, 20)
循环中断
Scala为了更好的适应函数式变成,去掉了 break、continue,推荐使用函数式的风格解决break和continue的功能,而不是一个关键字。
Scala中使用breakable控制结构来实现break和continue功能。
对于continue,可以使用循环守卫、if判断等方式实现。
对于break,可以通过抛出异常的方式实现退出。
例如:
try {for(i <- 0 until 5) {if (i == 3) {throw new RuntimeException}println(i)}} catch {case e: Exception => // 什么都不处理,只是接收异常然后退出循环}println("-----------------------")
使用breakable方式退出循环(本质上也是使用抛出异常的方式):
Breaks.breakable( // 包装了的try...catchfor(i <- 0 until 5) {if (i == 3) {Breaks.break() // 抛出异常}println(i)})println("---------------")
进一步:
import scala.util.control.Breaks._ // 引入Breaks下的所有方法// 进一步简写breakable(for(i <- 0 until 5) {if (i == 3) {break()}println(i)})
while和do…while循环
while和do...while的使用和Java语言中相同。
object Test {def main(args: Array[String]) {// 局部变量var a = 10;// while 循环执行while( a < 20 ){println( "Value of a: " + a );a = a + 1;}}}
object Test {def main(args: Array[String]) {// 局部变量var a = 10;// do 循环do{println( "Value of a: " + a );a = a + 1;}while( a < 20 )}}
对于Scala这种语言,更多的是应用于Spark这类的大数据场景下的,在这种场景下,不推荐使用while循环。因为 while语句不像for语句有yield,while没有返回值,所以当要用该语句来计算并返回结果时,就不可避免的要使用while外面定义的全局变量,这样就等同于循环内部的程序要操作外部的变量,对于大数据场景下不适用。而且while可以实现的功能,for语句都可以实现,所以推荐使用for循环。
