Scala學習筆記(12)-特質、包和引用

1.特質:trait是Scala裏代碼複用的基礎單元。特質封裝了方法和字段的定義,並能夠經過混入到類中重用它們。不像類的繼承那樣,每一個類都只能繼承惟一的超類,類能夠混入任意個特質。一旦特質被定義了,就能夠使用extends或with關鍵字,把它混入到類中。Scala程序員「混入」特質而不是繼承它們,由於特質的混入與那些其它語言中的多繼承有重要的差異。 程序員

特質就像是帶有具體方法的Java接口,不過其實它能作的更多。特質能夠,比方說,聲明字段和維持狀態值。實際上,你能夠用特質定義作任何用類定義作的事,而且語法也是同樣的,除了兩點。第一點,特質不能有任何「類」參數,也就是說,傳遞給類的主構造器的參數。換句話說,儘管你能夠定義以下的類:  ui

class Point(x: Int, y: Int)
可是下面定義特質的嘗試將遭到失敗:
trait NoPoint(x: Int, y: Int) // 編譯不過

類和特質的另外一個差異在於不論在類的哪一個角落,super調用都是靜態綁定的,在特質中,它們是動態綁定的。 scala

2.包 code

Scala裏把代碼放在包裏的另外一種方式很像C#的命名空間。在package子句以後用大括號包起來一段要放到包裏去的定義。除此以外,這種語法還能讓你把文件的不一樣部分放在不一樣的包裏。 對象

package bobsrockets.navigation {
    // 在bobsrockets.navigation包裏
    class Navigator package tests {
        // 在bobsrockets.navigation.tests包裏 class NavigatorSuite
    }
}

正如註釋所提示的,Scala的包的確是嵌套的。也就是說,包navigation從語義上在包bobsrockets內部。Java包,儘管是分級的,卻不是嵌套的。在Java裏,在你命名一個包的時候,你必須從包層級的根開始。Scala爲了簡化語言使用了更嚴謹的規則。 繼承

3.引用 索引

// 易於訪問bobsdelights的全部成員 接口

import bobsdelights._

Scala的按需引用寫做尾下劃線(_)而不是星號(*)(畢竟*是合法的Scala標識符! it

Scala引用能夠出如今任何地方,而不是僅僅在編譯單元的開始處。一樣,它們能夠指向任意值。例如: io

def showFruit(fruit: Fruit) {
    import fruit._
    println(name +"s are "+ color)//這裏的兩個索引等價於fruit.name和fruit.color
}

Scala的引用一樣能夠重命名或隱藏成員。能夠用跟在引用的成員對象以後的包含在括號裏的引用選擇子句:import selector clause作到。下面是一些例子:

import Fruits.{Apple, Orange}

此次只引用了對象Fruits的Apple和Orange成員。

import Fruits.{Apple => McIntosh, Orange}

此次從對象Fruits引用了Apple和Orange兩個成員。不過,Apple對象重命名爲McIntosh。所以這個對象能夠用Fruits.Apple或McIntosh訪問。重命名子句的格式是「<原始名> => <新名>」。

import Fruits.{_}

這個引用了對象Fruits的全部成員。這與import Fruits._同義。

import Fruits.{Apple => McIntosh, _}

這個從Fruits對象引用全部成員,不太重命名Apple爲McIntosh。

import Fruits.{Pear => _, _}

這個引用了除Pear以外的全部Fruits成員。「<原始名> => _」格式的子句從被引用的名字中排除了<原始名>。某種意義上來講,把某樣東西重命名爲‘_’就是表示把它隱藏掉。

總而言之,引用選擇能夠包括下列模式:
 簡單名x。把x包含進引用名集。
 重命名子句x => y。讓名爲x的成員以名稱y出現。
 隱藏子句x => _。把x排除在引用名集以外。
 全包括‘_’。引用除了前面子句提到的以外的全體成員。若是存在全包括,那麼必須是引用選擇的最後一個。

4.私有成員

class Outer {
    class Inner {
        private def f() {
        println("f")
        }
        class InnerMost {
            f() // OK
        }
    }
    (new Inner).f() // 錯誤:f不可訪問
}

Scala裏,(new Inner).f()訪問非法,由於f在Inner中被聲明爲private而訪問不在類Inner以內。相反,類InnerMost裏訪問f沒有問題,由於這個訪問包含在Inner類以內。Java會容許這兩種訪問由於它容許外部類訪問其內部類的私有成員。

Scala裏的訪問修飾符能夠經過使用修飾詞增長。格式爲private[X]或protected[X]的修飾符表示「直到」X的私有或保護,這裏X指代某些外圍的包,類或單例對象。

5.伴生對象

在Scala裏沒有靜態成員;代之以能夠擁有包含成員的僅存在一個的伴生對象。

Scala的訪問規則給予了伴生對象和類一些特權。類把它全部的訪問權限共享給半生對象,反過來也是如此。特別的是,對象能夠訪問全部它的伴生類的私有成員,就好象類也能夠訪問全部伴生對象的私有成員同樣。

相關文章
相關標籤/搜索