码迷,mamicode.com
首页 > 其他好文 > 详细

2 表达式 选择 循环 函数

时间:2015-05-21 19:02:54      阅读:175      评论:0      收藏:0      [点我收藏+]

标签:

Scala中,几乎所有的语法结构都是有值的(包括表达式和语句块...)

1 IF/ELSE结构

val s = if(x > 0) 1 else -1

等价于 if(x > 0) s = 1 else s = -1

 

注:既然表达式是有值的,那么必然也是有类型的。如上述表达式的类型是:Int

如果出现if分支和else分支类型不同,比如:if(x > 0) ”positive” else -1,那么整个表达式的类型是:String和Int的公共基类Any

 

如果一个表达式没有任何有效值,可以用Unit表示其类型,用()表示,相当于C++中的void:

如:if(x > 0) 1 else ()

 

默认情况下,Scala解释器只能解释一行代码,如果你想使用多行代码,如:

if(x > 0) 1

else if(x == 0) 0 else -1

则必须在else前加上{},如:

if(x > 0) {1

} else if(x == 0) 0 else -1

 

2 语句的结束

Scala中的语句结束时不需要加分号,除非一行内写了多条语句,如:

if (n > 0) {r = r * n; n -= 1}

 

如果想将一行比较长的语句写在多行中,断行时只要第一行最后一个字符不能作为语句结束符即可,例如:+ - …

s = s0 + s1 + s2 –

s3 –s4

 

如果是语句块的话,最好使用{,如:

if (n > 0){

    r = r * n

n -= 1

}

 

3 Scala的语句块

在Scala中,语句块{..}的结果是一个表达式,该语句块的值就是块中最后一个表达式的值

在Scala中,赋值语句的返回类型为Unit,因此不能出现链式赋值,如:x = y = 1,这是错误的

 

4 输入输出

输出:

print(“benxintuzi”)                           不带换行符

println(“benxintuzi”)                         带换行符

printf(“Hello, %s\n”, “benxintuzi”)           格式化输出

输入:

var name = readLine(“Your name :”),用于从控制台读取一行输入,其中的参数”Your name :”为提示符,此外,还可以如下读取不同类型的内容:

val v1 = readInt()/readDouble()/readByte()/readShort()/readChar()

 

5 循环

While/do循环结构与C++、Java无异

Scala中的for循环结构如下:

for(i <- 表达式)

例如,for(i <- 0 util s.length){ // [0, s.length - 1]

       Sum += s(i)

      }

说明:Scala中并没有提供break或者continue来退出循环,如果想实现退出循环,则可以使用如下方式:

1 使用Boolean型的控制变量

2 使用嵌套函数,从函数中return

3 使用Breaks对象中的break方法,如:

import scala.util.control.Breaks._

breakable{

    for(…){

       if(…) break;  // 退出breakable块

}

}

 

for循环的高级特性:

特性1:for(i <- 1 to 3; j <- 1 to 3) print(…) // 多个表达式

特性2:for(i <- 1 to 3; j <- 1 to 3 if i != j) print(…) // 注:只能加一个判断,并且前边不能有分号

特性3:for(i <- 1 to 3; from = 4 – i; j <- from to 3) print(…) // 可以使用任意多个定义

特性4:for(i <- 1 to 10) yield i % 3 // 以yield开始的循环体会构造出一个结果集合:Vector{1, 2, 0, 1, 2, 0, 1, 2, 0, 1}

 

6 Scala函数

1 非递归函数定义时可以不给出函数返回类型:

def abs(x : Int) = if(x >= 0) x else –x

2 递归函数必须给出返回类型:

def fact(n : Int) : Int = if(n <= 0) 1 else n * fact(n - 1)

如果没有类型,Scala解释器无法确定n * fact(n - 1)的类型是Int(回忆一下: C/C++中的结构体中,不能有包含自身的变量,但是可以有指向自身的指针,就是因为编译器无法确定结构体的大小)

3 默认参数和指定参数

def decorate(str : String, left : String = “[”, right : String = “]”) = left + str + right // left和right都带有默认值 

调用decorate(“benxintuzi”)-----[benxintuzi]

调用decorate(“benxintuzi”, “<”, “>”)-----<benxintuzi>

 

注:在调用时,可以显示指定某个参数的值,其顺序没必要和定义时一致,如:

decorate(left = “((”, str = “tuzi”, right = “))”)-----((tuzi)) [但是不建议这样做,最好保持定义时的顺序]

4 变长参数

def sum(agrs : Int*) = {

    var result = 0

    for(arg <- args) result += arg

    result

}

可以使用任意多个参数调用sum,如:val s = sum(1, 2, 3)

 

注意:如果传入的是单个区间,如val s = sum(1 to 5),则必须告诉编译器将这个参数当作序列Seq来处理,具体如下:

val s = sum(1 to 5 : _*),该语法在递归函数中常用

 

7 过程

如果一个函数不需要返回有效值,可以使用过程来表示,具体如下:

def box(s : String){

    Var border = “-” * s.length + “--\n”

    Println(border + “|” + s + “|\n” + border)

}

 

等价于:

def box(s : String) : Unit = {

    Var border = “-” * s.length + “--\n”

    Println(border + “|” + s + “|\n” + border)

}

 

8 Lazy Value

当val被声明为lazy时,其初始化将被推迟到首次对其调用时:

Lazy val words = scala.io.Source.fromFile(“/usr/share/dict/words”).mkSring

只有调用words时,才会打开这个文件。该机制对于开销比较大的初始化语句十分有效。

 

9 异常

Scala中的异常机制与C++和Java类似。比如,throw new IllegalArgumentException(“x should not be negative”)

和Java一样,抛出的异常对象必须是java.lang.Throwable的子类。

throw表达式的类型是Nothing

捕获异常采用的是模式匹配语法:

try{

    Process(new URL(“…”))

} catch{

    case _ : MalformedURLException => println(“Bad URL”)

    case ex : IOException => ex.printStackTrace()

}

注:在不需要使用捕获到的异常时,用 _ 代替变量名

 

                                                                 -----源自《快学Scala》 Chapter 2

2 表达式 选择 循环 函数

标签:

原文地址:http://www.cnblogs.com/benxintuzi/p/4520374.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!