2012-01-05 9 views
5

私は型チェックカリーとuncurried一般的な機能間の違いで混乱ビットだ:私の直感はx(1, "one")y(1)("one")両方が型エラーを与えるべきであるということでしたが、私が間違っていた汎用型統合:複数パラメータ(T、T)対複数パラメータリスト(T)(T)?

scala> def x[T](a: T, b: T) = (a == b) 
x: [T](a: T, b: T)Boolean 
scala> def y[T](a: T)(b: T) = (a == b) 
y: [T](a: T)(b: T)Boolean 

scala> x(1, "one") 
res71: Boolean = false 
scala> y(1)("one") 
<console>:9: error: type mismatch; 
found : java.lang.String("one") 
required: Int 
       y(1)("one") 
       ^

は、最初に私が起こっている暗黙的キャストのいくつかの並べ替えがあったと思ったが、それはケースのようには思えなかった。

scala> x(1 :Int, "one" :String) 
res73: Boolean = false 

何が起こっているのですか?私の直感は何ですか?

+0

私は長い時間前にこのの重複を見てきました。私はまた、この[ほぼ]正確なケースがSLSに記録されていると信じています。 –

+0

そこに行きます。 SLSで議論されている重要な用語 "multiple parameters lists"でタイトルを更新しました:) –

答えて

9

私は、最初のケースでは、それは(ダウンキャスト?)アップキャストされていることの両方の引数が、このようなTと思います:どれ。 2番目の方法では、Intをカリングして文字列に失敗します。

これは、私を負担するようです:

scala> y(1)_ 
res1: Int => Boolean = <function1> 
+0

これは 'y(1:Any)(" hello ")'が 'false'を返すので、おそらくそうです。 – rampion

+0

興味深い側面注意点として、この –

+0

のいくつかのより多くの証拠のための私の編集を参照してください、この質問は、ここで作られたアサーションに呼び出すようだ:http://www.scala-lang.org/node/262「というその後、F(X )(y)とg(x、y)はまったく同じコードにコンパイルされます。 –

10

Scalaは一度の種類を一個のパラメータブロックを決定しようとします。あなたが別のパラメータを追加し、部分的に適用する場合は、これを見ることができます:もちろん

def x[T](a: T, b: T)(c: T) = (a == b) 
scala> x(1, "one") _ 
res0: Any => Boolean = <function1> 

IntString両方がAnyある(と==Any上で定義されます)。以前のブロックで使用されていない

タイプのパラメータは、後にブロックで使用されて自由に残る:

def y[T,U](a: T)(b: U)(c: (T,U)) = (a == b) 
scala> y(1)("one") 
res1: (Int, java.lang.String) => Boolean = <function1> 

ます。また、後でブロックのデフォルト値として、以前のブロックを使用することができます!

def z[T,U](a: T)(b: U)(c: (T,U) = (a,b)) = (c._1 == c._2) 
scala> z(1)("one")() 
res2: Boolean = false 

このように、複数のパラメータブロックの中で、あなたのパラメータを配布することは型推論のためおよび不履行のための(部分的なアプリケーションのための)両方の影響を持っています。

関連する問題