2011-01-24 81 views
3

我正在嘗試編寫一個簡單的幫助程序方法,該方法接收可以關閉的內容以及接收前者的某些函數,並確保在執行該函數後關閉「可關閉」。爲什麼這種結構類型綁定不能按預期工作?

例如,我想用這樣的:

closing(new FileOutputStream("/asda"))(_.write("asas")) 

我IMPL是

object Helpers { 

    def closing[T <: { def close }](closeable: T)(action: T => Unit): Unit = 
    try action apply closeable finally closeable close 

} 

但是,試圖編譯這個簡單的測試時:

object Test { 

    import Helpers._ 

    closing(new FileOutputStream("/asda"))(_.write("asas")) 

} 

編譯器抱怨:

推斷類型參數 [java.io.FileOutputStream中]不 符合方法收盤的類型 參數界限[T <:AnyRef {DEF 接近:單位}]

任何想法,爲什麼?

回答

11

你需要寫

def closing[T <: { def close() }] 

有沒有括號空括號和方法方法之間Scala中的一個區別的。

+0

而`FileOutputStream.write`顯然不能接受一個字符串。在字符串上調用`getBytes()`。 – Malvolio 2011-01-24 22:49:23

7

類型邊界很棘手。特別是,除了參數本身之外,Scala還會跟蹤參數列表的數量。試試這些!

class A { def f = 5 } 
class B { def f() = 5 } 
class C { def f()() = 5 } 
def useA[X <: { def f: Int }](x: X) = x.f 
def useB[X <: { def f(): Int }](x: X) = x.f 
def useC[X <: { def f()(): Int}](x: X) = x.f 

useA(new A) // This works, but what other combinations do? 

在你的情況,你想

def closing[T <: { def close() }] ... 

附:如果你使用這個有很多真正的計劃,你可能應該也與

class D extends B { override def f = 6 } 
class E extends A { override def f() = 6 } 

玩,看看你需要在每種情況下要使用的use

相關問題