scala流程控制
Scala 流程控制:顺序、分支与循环的优雅实现
流程控制是编程语言的基础,用于控制代码的执行顺序。Scala 作为一门多范式语言,在流程控制上既保留了与 Java 相似的语法,又融入了函数式编程的特性,尤其在循环和中断处理上有独特设计。本文详细介绍 Scala 的三大流程控制语句。
顺序控制
顺序控制是最基础的流程模式,代码按照从上到下的顺序依次执行,没有跳转或分支。这是所有编程语言的默认执行方式,Scala 也不例外。
// 顺序执行示例
val a = 10
val b = 20
val sum = a + b
println(s"a + b = $sum") // 先计算sum,再打印结果
特点:
- 无特殊关键字,代码自然流淌。
- 适用于简单的步骤化操作(如变量定义、计算、输出)。
分支控制(if…else)
Scala 的分支控制通过 if...else if...else 实现,与 Java 语法相似,但更灵活 ——if 表达式有返回值,可直接赋值给变量。
基本语法
val age = 19
// 多分支判断
if (age > 22) {
println("这么大岁数了,什么时候结婚生孩子呀")
} else if (age > 18) {
println("有对象了吗")
} else if (age > 16) {
println("好好学习,可不能早恋耽误学习")
} else {
println("你还小")
}
作为表达式的 if
Scala 中 if 是表达式(有返回值),而非单纯的语句。这意味着可以将 if...else 的结果直接赋值给变量。
val score = 85
val result = if (score >= 60) "及格" else "不及格"
println(result) // 输出:及格
// 复杂分支的返回值
val grade = if (score >= 90) "A"
else if (score >= 80) "B"
else if (score >= 60) "C"
else "D"
println(grade) // 输出:B
无返回值的分支
若分支不需要返回有意义的值,可返回 Unit 类型(类似 Java 的 void),用 () 表示。
val x = 3
val res = if (x > 5) 10 else () // else分支返回Unit
println(res) // 输出:()
优势:
- 避免临时变量,直接通过
if表达式赋值,代码更简洁。 - 支持函数式编程风格,可作为高阶函数的参数。
循环控制
Scala 提供 for、while、do...while 三种循环,其中 for 循环功能最强大,支持多种遍历方式;while 和 do...while 则与 Java 用法类似,但 Scala 更推荐使用 for。
for 循环:灵活的遍历工具
Scala 的 for 循环(也称 “for 推导式”)支持范围遍历、集合遍历、守卫条件、变量引入等,语法灵活。
(1)范围遍历
to关键字:左闭右闭区间(包含起止值)。until关键字:左闭右开区间(包含起始值,不包含结束值)。
// 1 to 3:遍历1、2、3(左闭右闭)
for (i <- 1 to 3) {
print(i + "\t") // 输出:1 2 3
}
println()
// 1 until 3:遍历1、2(左闭右开)
for (i <- 1 until 3) {
print(i + "\t") // 输出:1 2
}
(2)集合遍历
直接遍历数组、列表等集合元素:
val fruits = Array("apple", "banana", "orange")
for (fruit <- fruits) {
println(fruit) // 依次输出数组中的元素
}
(3)循环守卫(条件过滤)
通过 if 条件过滤循环元素,类似 continue 的效果(只执行满足条件的迭代)。
// 遍历1-5,只打印偶数
for (i <- 1 to 5 if i % 2 == 0) {
print(i + "\t") // 输出:2 4
}
// 等价于带if判断的普通循环
for (i <- 1 to 5) {
if (i % 2 == 0) {
print(i + "\t")
}
}
(4)引入临时变量
在循环中定义临时变量,简化操作(多个表达式用分号分隔)。
// 遍历1-3,同时计算i的平方
for (i <- 1 to 3; square = i * i) {
println(s"$i 的平方是 $square")
}
// 输出:
// 1 的平方是 1
// 2 的平方是 4
// 3 的平方是 9
(5)嵌套循环
通过多个生成器实现嵌套循环,无需多层缩进。
// 嵌套循环:遍历1-2和3-4的组合
for (i <- 1 to 2; j <- 3 to 4) {
println(s"i=$i, j=$j")
}
// 输出:
// i=1, j=3
// i=1, j=4
// i=2, j=3
// i=2, j=4
while 循环
while 循环先判断条件,满足则执行循环体,语法与 Java 一致。
var i = 0
while (i < 5) {
println(s"line $i")
i += 1 // 注意:Scala中没有i++,需用i += 1
}
// 输出:
// line 0
// line 1
// line 2
// line 3
// line 4
注意:
- Scala 不推荐频繁使用
while,因为它依赖可变变量(如i),不符合函数式编程的 “无副作用” 原则。 - 优先用
for循环替代,尤其是遍历集合时。
do…while 循环
do...while 先执行循环体,再判断条件,确保循环体至少执行一次。
var count = 3
do {
println(s"count = $count")
count -= 1
} while (count > 0)
// 输出:
// count = 3
// count = 2
// count = 1
循环中断:打破常规的函数式实现
Scala 没有 break 和 continue 关键字,而是通过 Breaks 工具类的 break() 和 breakable() 实现循环中断,本质是通过异常机制控制流程。
使用步骤:
- 导入
scala.util.control.Breaks。 - 用
breakable()包裹循环体(用于捕获中断异常)。 - 用
break()触发中断(抛出特殊异常)。
import scala.util.control.Breaks._
// 遍历1-10,遇到5则中断循环
breakable {
for (i <- 1 to 10) {
if (i == 5) {
break() // 触发中断
}
print(i + "\t")
}
}
// 输出:1 2 3 4
原理:
break()抛出BreakControl异常。breakable()捕获该异常并忽略,避免程序终止。
模拟 continue 效果
结合循环守卫,可实现类似 continue 的功能(跳过当前迭代):
// 遍历1-10,跳过偶数
for (i <- 1 to 10) {
breakable {
if (i % 2 == 0) {
break() // 跳过当前迭代
}
print(i + "\t")
}
}
// 输出:1 3 5 7 9
流程控制的最佳实践
- 优先用 for 循环:
for推导式功能强大,支持多种遍历场景,且更符合 Scala 风格。 - 利用 if 表达式的返回值:减少临时变量,例如
val result = if (cond) a else b。 - 慎用 while 循环:尽量用
for或递归替代,避免可变变量。 - 合理使用循环中断:
breakable+break是 Scala 推荐的中断方式,清晰且安全。