控制结构是实现业务逻辑的基础,scala提供了基本的控制结构 if..else、do…while、while.. for..等,下面我们用具体的示例来对这集中结构做简要说明。
在java、c或其他的编程语言中,if…else…是作用是控制流程分支,但scala除此之外,还提供为if..else..提供了一个更强大的功能:带返回值。实际上这也是scala语言的一大特点:几乎所有的表达式都带有返回值。
根据一个boolean条件来决定程序的执行流程
//第一个作用 逻辑控制
val x = 10
if(x > 10) {
println( "x 大于10" )
}else {
println( "x 小于10" )
}
scala不支持三木运算符 boolean ? a : b
,但这可以用if..else..轻松实现,因为scala中的if..else..带有返回值
//第二个作用 变量初始化
val isOpen = if( x > 10) true else false
println(isOpen) //false
val result1 = if ( x > 10) x + 10 else x - 10
println(result1) //0
需要注意的是,当if 的返回值类型 与 else的返回值类型不同时,最终返回值类型是 两种类型的并集
val result2: Any = if(x > 10) "bigger than 10" else x - 10
println(result2)
上面的例子中,String和Int两种类型的并集类型为Any,所有result2是一个Any类型的引用。
另外,若只有 if 没有else 会怎么样呢?看下面的例子
val result3 = if(x > 10) 10
println(result3) // () Unit
是的,result3并不是没有值,它的值是 (),即Unit,类似于java中的void,这确实有点 难以理解,但这复合scala的编码风格,你会习惯的…
while、do..while的用法和java或c基本相同,但有一点区别,scala中的while、do…while是有返回值的,返回值类型为Unit,即 ()
var y = 10
val a = do {
println(y)
y -= 1
}while(y >= 0)
println("a:" + a) // a:()
var z = 10
val b = while(z >= 0) {
println(z)
z -= 1
}
println("b:" + b) //b:()
scala并没有对java格式的for进行支持,scala的for看起来更像是java中的增强for,利用他,你可以对数组,集合, 字符串等进行遍历,但这仅仅是scala中for的基本功能
val array = Array("1","2","3","4","5")
for(a <- array){
print(a + ",")
}
val list = List[Int](1, 2, 3, 4, 5, 6, 7)
for(l <- list) {
print(l + ",")
}
val set = Set("a","b","c","d")
for(s <- set) {
print(s + " ")
}
for(s <- "HelloWorld"){ print(s + ",") }
for(i <- 0 to 10) {
print(i + ",") // 0 - 10
}
println()
for(i <- (0 until(10, 2)) ) {
print(i + ",") // 0,2,4,6,8,
}
//遍历map
val map_1 = Map("1"->"a", "2"->"b", "3"->"c")
for((k, v) <- map_1) {
print(k + "," + v + " ")
}
println()
for((_, v) <- map_1) {
print(v + " ")
}
从上面的例子中,我们已经看出,scala中的for要比java中的for强大很多,但这还没有结束,你还可以为scala中的for雇佣一个大爷来看大门,告诉他什么人可以进,什么人不可以进,他就会严格的执行你的安排,像下面这样
for(l <- list if l > 5) {
print(l + ",") // 6, 7
}
这看起来确实很有意思,而且也很有用。
有时,你可能想利用遍历出来的每一个值产生一个中间变量,在scala中这是完全可以的
//定义
for(i <- 1 to 10; j = 10 - i) {
print(i + "," + j + " ")
}
从上面我们看出,循环分为两类,do..while和while属于一类,for为另一类,第一类的执行依赖于一个boolean值,所以我们可以用一个boolean值来控制循环的执行
var flag_1 = true
var i_1 = 0
while(flag_1) {
i_1 += 1
if(i_1 == 5) flag_1 = false
}
var flag_2 = true
var i_2 = 0
do{
i_2 += 1
if(i_2 == 6) flag_2 = false
}while(flag_2)
对于for循环,我们可以通过break或嵌套函数的方式来跳出,对于break这种方式,scala中并没有像java中的break关键字,我们必须借助Breaks对象来完成,就像下面这样
import scala.util.control.Breaks._
breakable {
for(i <- 1 to 10) {
if (i == 5) break()
println(i)
}
}
这看起来很怪,但就是这样用的。需要注意的是,这种方式并不好,我们先来看一些Breaks对象的源码
关键代码如下所示:
...
def breakable(op: => Unit) {
try {
op
} catch {
case ex: BreakControl =>
if (ex ne breakException) throw ex
}
}
....
def break(): Nothing = { throw breakException }
我们可以看到,for被当做一个函数来执行,而break则是throw exception,也就是说break的底层是通常抛异常的形式强硬的中断了for的执行,这样的执行逻辑效率是保证不了的。
当然,我们还有办法:嵌套函数+return。这看起来更怪异
for(i <- 1 to 10){
print(i + "-")
if(i > 7) return
}
}
aa()
为什么要这样呢??
好了,先到这吧,欢迎补充 and 挑刺。