2011-11-27 84 views
0

查找發現Scala的內部類:不能在這個例子

class Outer(private val handler: Actor){ 
    def this() = this(new Handler) // type Handler not found ? ? 

class Handler extends Actor{ 
    override def act() { 

    } 
    } 
} 

編譯器抱怨類Handler沒有找到。這是一個錯誤?

回答

4

內部類Handler對外部類實例有引用,並且您正試圖在外部實例存在之前創建new Handler - 這是不可能的。

你可以嘗試這樣的事情,而不是:

class Outer(h: Actor = null) { 

    private val handler = 
    if (h != null) h 
    else new Handler 

    class Handler extends Actor { 
    override def act() { 

    } 
    } 
} 

如果你擔心使用null,您可以使用the solution described here更換null在參數的缺省值。

+0

什麼好的解決辦法! –

2

首先,您可能知道訪問內部類是通過點(。)運算符。因此訪問Handler類應該是Outer.Handler。當你在this範圍內時,編譯器找不到Handler類,因爲內部類與外部對象綁定。在這裏,一切都得到了更好的解釋:http://www.scala-lang.org/node/115。總之,你會得到一個完全不可能的情況,因爲內部類隱藏在外部類中,但外部類的實際實例化需要內部類...

有很多方法可以解決它我猜,我在這裏快速畫出一張。由於您可能希望Handler類以某種方式綁定到Outer,所以我建議創建並對象,然後從這裏調用Outer類。因此,你會得到大致相同的語法,並且所有內容都存儲在一個地方。它可能是這個樣子:

class Outer(private val handler : Actor) 

object Outer { 
    class Handler extends Actor { override def act { } } // The "inner" class 
    def apply() = new Outer(new Handler) 
    def apply(handler : Actor) = new Outer(handler) 
} 

希望幫助:)

+0

如果在對象「Outer」中定義了「Handler」,則只能寫入'Outer.Handler',因此不會引用實際外部對象的實例。你正在改變OP的語義。 –

+0

呃我不確定你的意思。我的觀點是,我認爲改變結構來創建外部對象而不是推斷外部對象更容易。對我來說,它更加乾淨。特別是如果我能避免可變結構。 –

+0

您的'Handler'類沒有引用外部對象,因此,即使它看起來比較乾淨,您也正在改變OP所希望的語義。我的解決方案不(也不使用可變結構)。 –

相關問題