Scalaにおけるη展開


拡張


"Can you tell me about Eta Expansion?"


凍った.私のパルスは、温度上昇、喉の乾燥を開始した.私は、メソッドと機能について何かをつぶやきました、そして、どのようにScalaはOOです.しかし、私は知っていなかった、ごめんなさい!じっと見つめてください.
これは、Scala契約のインタビューにおいて、かなり無邪気な質問に対する私の反応でした.その仕事は決して来なかった.会社は明らかにオファーを作りたがっていた.しかし、私はそれが私の没落につながったその質問への一貫した答えの私の不足であると考えるのを助けることができません!
ちなみに、これはインタビューの状況にある典型的な反応ではない.幸いにもコーディングの問題を解決するためのテキストブックのプロセスの説明とすべてのインスタントリコールとは何の関係もないが、本当に良い方法は、30分のインタビューでは、テストすることはありません.だからここにいる.
このブログは、その質問に対する実際の答えを書き留める試みです.そうすることで、Scalaにも、また一般的にFPにも余分な洞察を得ることができます.

ETA拡張は何ですか?


FPのコア・テネシーの1つは、機能が一流の市民であるということです.あなたが値で何かをすることができるならば、あなたは機能でそれをすることができます.リストクラスのメソッドマップの定義を考慮する
final def map[B](f: (A) => B): List[B]
その地図を見ることができるList[A] a型からb型までの要素をマップする引数として関数を受け取り、List[B]それで、我々は数をそうストリングに変えることができます
List(1, 2, 3).map(n => n.toString)
これまでのところ、機能的です.匿名関数はmapのシグネチャを満たし、関数a => b(この場合はint => string)を受け取ります.
しかし、もし我々がメソッドを渡したいならば.我々はスカラがOOであるので、我々が言うとき、知っています
def f(n: Int): String = ...
それから、Fは我々が働いているクラスで、そして、機能でないメソッドです.関数を定義する
val f: (Int) => String = ...
そして(scala 2 . xにおいて)私たちはリスト(第1のクラス、覚えている)で機能を置くことができます
val fFunction: (Int) => String = ...
def fMethod(n: Int): String = ...
List(fFunction) // ok
List(fMethod)   // not ok
(これはScala 3の場合ではありません.これはETA拡張を可能にしました.これを可能にし、自動拡張された関数のサポートを追加しました).
しかし、SECの上でハングして、私のScalaコンパイラは陽気に許します
def f(n: Int): String = 
....
List(1, 2, 3).map(f)
そして、これはeta拡張が入るところです.フィル!それはそれがどのように動作するか触れずに行く長い道のりです.
このような関数を定義するときに注意する価値があります
val f: (Int) => String = ...
これは構文上の砂糖です、そして、本当に、フードの下にあるのは形質機能を実装するオブジェクトです、あるいは、特にこの場合
Function1[Int, String]
そして、それは関連付けられたApplyメソッドです.
それで、我々はそれを持っていました.特に、Scala 3ではアンパックにはもっとたくさんあります.だから私は将来これに戻るかもしれません.