2011-08-24 31 views
14

假設你有以下幾點:斯卡拉,柯里和重載

foo(x: String)(y: Int): Int 
foo(x: String)(y: Double): Int 

斯卡拉不允許這樣的表達。據我所知,其原因是foo(「asdf」)沒有明確定義的類型(它是Int => Int或Double => Int)。

爲什麼不應該允許這種「多種」功能的原因是什麼?

+0

https://issues.scala-lang.org/browse/SI-2628 – Bradford

+0

Scala允許你定義這對重載方法,但是它的任何調用都是不明確的,由Martin下面概述的原因。相關:http://stackoverflow.com/questions/2510108/why-avoid-method-overloading – retronym

回答

19

Scala中的重載分辨率只考慮了第一個參數列表。這就是爲什麼替代品必須在此列表中有所不同。有一個很好的理由:然後我們可以使用已解析函數的類型來推斷後續參數的類型。這使得像成語:

xs.corresponds(ys) { (x, y) => x < y } 

注意,這裏我們需要知道的corresponds類型,以推斷類型的xy。如果corresponds過載,讓這種情況發生,這將是一件恥辱。

+0

感謝您的回答。作爲後續工作,根據對應的重載版本的範圍(類似於implicits的工作方式)並且僅僅根據這些關係來決定可能的類型是否有可能分配給x和y的列表只有在必須時纔會鍵入? 或者這會違背靜態類型的想法嗎? –

+0

@Martin Odersky你能看到http://stackoverflow.com/q/7291168謝謝! –

+2

考慮可能類型列表的任何方法都有可能導致類型檢查時間呈指數級增長。這就是爲什麼Scala在其類型推斷算法中通常不這麼做的原因。 –

2

這不是第一次詢問:it was asked back in 2009。不幸的是,馬丁並沒有明確說明問題是什麼,除了需要對超載的工作方式進行相當廣泛的規範改變之外。我已經看過這個規範,但是我不清楚核心問題在哪裏,但是我沒有足夠的技巧來給出明確的答案。

+1

這是一個稍微不同的問題。在你連接的問題中,你有兩個函數,它們只會在返回類型中有所不同('foo(x:Bar):Unit' vs.'foo(x:Bar)):Function1 [Bar => Baz,Unit] ')如果我的推理是正確的(仍然不完全相信...) – Dirk

+0

我不明白爲什麼_issue_是不同的。問題出現的條件可能不同,但我認爲問題是相同的。我嘗試了各種操作,但錯誤從未改變。我認爲,重載是很早就完成的,或者優先於「x」。 –

+0

我不確定這是一樣的。在你鏈接的scala問題中,有兩個函數是有意義的,因爲foo()和foo()_是不同的,而在當前情況下,沒有不同的方式來表達兩個可能的foo() _ 功能。 潛在的原因可能是一樣的,但我不相信。實際上,我認爲這也是德克的觀點。 –