探索Scala(1)-- 運算符重載

Scala語言運算符重載完全是語法層面的小把戲,本文記錄我對Scala語言運算符重載的一些理解。

方法調用語法糖

調用方法時,Scala允許省略點號圓括號,如下面代碼所示:


把運算符映射成單詞

對於Scala來說,運算符和普通的方法沒什麼兩樣。比如下面這個類就重載了加號減號


我們可以這樣使用MyInt:

var myInt = new MyInt(1)
myInt = myInt + 1
javap或者classpy分析一下scalac編譯之後的類可以知道,+實際上被編譯成了$plus()方法,-被編譯成了$minus()方法。也就是說,下面三行代碼完全等價:

myInt = myInt + 1
myInt = myInt.+(1)
myInt = myInt.$plus(1)

多符號運算符

多符號運算符無非就是單個運算符的簡單組合而已,給MyInt添加一個多符號運算符+++,如下所示:

那麼可以這樣使用+++:

var myInt = new MyInt(1)
myInt = myInt +++ 1

反編譯MyInt.class可以知道,scalac把+++運算符編譯成了$plus$plus$plus()方法。

op=語法糖

如果一個類重載了op運算符,但是沒有重載op=,那麼Scala編譯器會把x op= y替換爲x = x op y,也就是x = x.op(y),代碼如下所示:

var myInt = new MyInt(1)
myInt += 1 // myInt = myInt + 1

綁定規則

如果運算符以冒號結束,那麼運算符會綁定(bind)到右邊的操作數,也就是說,x op: y等價於y.op:(x)。我們給MyInt增加一個+:運算符,如下所示:


那麼可以這樣使用+:運算符:

var myInt = new MyInt(1)
println(1 +: myInt) // myInt.+:(1)


一元運算符

只有四種運算符可以被定義爲一元(Unary)運算符,它們是:+、-、!、~,如下面代碼所示:

下面是示例代碼:

val myInt = new MyInt(1)
println(-myInt) // -1
println(!myInt) // 99
println(~myInt)

圓括號語法糖

如果一個類定義了apply()方法,那麼Scala提供了語法糖,讓該類的實例看起來像是函數(可以直接調用)或數組(可以按下標訪問元素)。如果類定義了update()方法,那麼就可以像數組那樣按下標賦值。比如下面的Pair類:


可以像下面這樣使用Pair類:

val xy = new Pair(Array(3, 7))
println(xy(0)) // 3
println(xy(1)) // 7

xy(0) = 11
xy(1) = 18
println(xy(0)) // 11
println(xy(1)) // 18

運算符對照表

下面是我整理出來的運算符和Scala內部名稱的對照表:

+ $plus
- $minus
* $times
/ $div
% $percent
& $amp
| $bar
^ $up
~ $tilde
> $greater
< $less
! $bang
? $qmark
= $eq
: $colon
@ $at
# $hash
\ $bslash
$ $

參考資料

http://www.scala-lang.org/documentation/

http://stackoverflow.com/questions/7888944/scala-punctuation-aka-symbols-and-operators

《Programming in Scala》第二版

《Scala for the Impatient》


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章