2016-09-16 3 views
0

(1)はスカラREPLに二つの機能定義した:(2)ブラケットなしでそれらを構成スカラ関数組成:ブラケットとタイプ

scala> def f(s: String) = "f(" + s + ")" 
f: (s: String)String 

scala> def g(s: String) = "g(" + s + ")" 
g: (s: String)String 

が期待通りに動作します。

scala> f _ compose g _ 
res18: String => String = <function1> 

(3)括弧で囲んで指定しないでください:

scala> f(_).compose(g(_)) 
<console>:14: error: missing parameter type for expanded function ((x$1) => f(x$1).compose(((x$2) => g(x$2)))) 
     f(_).compose(g(_)) 
     ^
<console>:14: error: missing parameter type for expanded function ((x$2) => g(x$2)) 
     f(_).compose(g(_)) 
        ^
<console>:14: error: type mismatch; 
found : String 
required: Int 
     f(_).compose(g(_)) 
        ^

質問1:なぜ誰かが説明できますか?

質問2:なぜタイプが一致しないのですか? ScalaはなぜIntを期待していますか?

(4)ブラケット付き周辺f(_)は、最初の2つのエラーが離れて行くことで、少し助けているようだ:

scala> (f(_)).compose(g(_)) 
<console>:14: error: missing parameter type for expanded function ((x$2) => g(x$2)) 
     (f(_)).compose(g(_)) 
        ^

は質問3:なぜこれらのブラケットは助けるのですか?

質問4:はなぜScalaは、彼らが明確にそれぞれfgで定義されているにもかかわらず、パラメータ型を必要とするのか?

(5)最後に、パラメータの種類を追加すると、それが動作します:

scala> (f(_)).compose(g(_:String)) 
res22: String => String = <function1> 

あなたは、組成物を達成するために何が起こっているかを説明し、代替構文を提供していただけますか?

ありがとうございました。

答えて

2

あなたはマジックショーのコメントを使用して(予想外の)展開を見ることができます:

scala> f(_).compose(g(_)) // show 
[snip] 
     val res0 = ((x$1) => f(x$1).compose(((x$2) => g(x$2)))) 

関数リテラルは、あなたが示したように、制約のparamsを必要としています。 f _はエター・エキスであり、x => f(x)の砂糖であるf(_)とは異なります。

意図しないアプリケーションf(x$1)は、インデックス作成のためにInt => Charという文字列を返します。追加された型の不一致が発生します。

アンダースコアは、1つの標準を含む多くのSO質問でカバーされています。

関連する問題