2013-12-22 83 views
2

我看到這個代碼是很常見的:自我註釋,爲什麼要用self:=>而不是val?

trait A { this: B => ... } 
trait A { self: B => ... } 

但我想知道,爲什麼不利用這個:

trait A { 
    val self: B = this 

    //.... 
} 

它這將是一個無限循環?

UPDATE:

這些是一樣的嗎?

trait A { self => ... } 
    trait A { val self = this } 

回答

1

我認爲,在大多數有用的情況下,你的第二個版本(使用字段)根本不會編譯。

trait A { self: B => ... } 

什麼的代碼段說的是,在A特質必須混合任何類也有類型B。例如,如果您正在編寫僅用於Logger類的特徵,則可以使用trait X { self: Logger => ... }與編譯器通信,X特徵僅用作Logger類的混合。

相反,你的替代解決方案意味着完全不同的東西:

trait A { 
    val self: B = this 

    //.... 
} 

該代碼將編譯當且僅當B :> ABA超類型)。我想不出任何有用的情況。即使您的嵌套類可能隱藏了外部this,仍可以使用類似Java的OuterClassName.this語法獲取封閉類的this引用。

+0

請看我的更新。 –

+0

@Alex - [self-type annotation syntax](http://docs.scala-lang.org/tutorials/tour/explicitly-typed-self-references.html)創建'this'的*別名*(即編譯器會用正確的'this'引用來替換'self'),而當你聲明'val self = this'時,你實際上會創建一個額外的字段。 – DaoWen

+0

我知道。我在問這個區別。只有一個領域的開銷? –

1

我不認爲有任何顯著差異 您可以隨時更換

trait A { bla: B => }; trait AA extends A with B 

trait A { def bla: B }; trait AA extends A { val bla = new B } 
當然AA的

是不是在這種情況下,一個B的實例,但是這看起來就像不泄漏實施細節的好處

+0

我想你的答案是實際上表明它們有所不同。第一種意味着一種「是 - 一種」關係,而第二種意味着「有 - 一種」關係(即繼承與構成)。然而,我很困惑這個作文例子在這裏如何應用,因爲OP是在具體詢問這個'this'。 – DaoWen

+0

is-a隱含了純粹的'extends B','這個:B'更好地反映了好的老作曲imo – OlegYch

+0

由於'this:B'語法的主要用途是創建混入特徵,在'B'中的具體行爲,我不同意這個構成是一個合理的替代。 – DaoWen

相關問題