Scala 2.13 から入る byname implicit arguments

github.com

mergeされてました。それの簡単な説明や、以前から自分がやりたかったやつを試したらうまくいったので、実例の紹介をします

そもそもSIPまであり

SIP-NN - Byname implicit arguments | Scala Documentation

pull requestにも、言語仕様への記述追加含め結構詳しく書かれているので、それ読めば特に書くことはないわけですが、一応説明します。

(これまたpull reqにも書かれていますが)一言で言うとshapelessのLazy相当のものをScala標準で出来るようになった、ということでしょうか。pull reqの例そのまま引用しますが、以下のようにimplicit parameter部分はbynameにできなかったわけですが、それが出来るようになります。 implicit部分がbynameにできないと何が不便か?というと、例えば再帰的なデータ型の型クラスのインスタンスが普通には作れなかったりします。 (higher kindなものを作ったりする、などの工夫が必要 Add higher kinded versions of `Eq`, `Order`, `Show` · Issue #2308 · typelevel/cats · GitHub )

trait Foo { def next: Foo }
object Foo {
  implicit def foo(implicit => rec: Foo): Foo = new Foo { def next = rec }
}

というわけで、具体例として4年半くらい前に悩んだこれがshapelessなしで出来るようになりました。めでたい

xuwei-k.hatenablog.com

scalaz.Free and scalaz.Cofree instances by xuwei-k · Pull Request #9 · typelevel/shapeless-contrib · GitHub

gist.github.com