ということで今日はPureを書きます。
Pure
Pureは"型パラメータを1つとる型"を型パラメータにとり、値を包み込む関数を持ちます。
分かりにくいので例を挙げます。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
case class ScalaChan[A](value: A) | |
implicit def ScalaChanEqual[A]: Equal[ScalaChan[A]] = equalA | |
implicit def ScalaChanShow[A]: Show[ScalaChan[A]] = showA | |
implicit def ScalaChanPure = new Pure[ScalaChan] { | |
def pure[A](a: => A) = ScalaChan(a) | |
} | |
"Scalaちゃん".pure[ScalaChan] assert_=== ScalaChan("Scalaちゃん") |
Pureを利用した関数では、計算をして結果を包むものが多いです。
pure
型を渡し、値をその型で包みます。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
1.pure[List] assert_=== List(1) | |
"Scalaz".pure[Option] assert_=== "Scalaz".some | |
'Scalaz.pure[Function0] assert_=== (() => 'Scalaz) |
iterate, repeat, replicate
iterate, repeatは無限リストなんかを作る関数。
Stream以外に使えるものはあるのだろうか?
replicateはiterate, repeatと似ているけれど、大きさが決まっています。
これはListなどでも使えます。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
1.iterate[Stream](1 +).take(3) assert_=== Stream(1, 2, 3) | |
1.repeat[Stream].take(3) assert_=== Stream(1, 1, 1) | |
1.replicate[List](3) assert_=== List(1, 1, 1) | |
lazy val nextPrime: Int => Int = _.doWhile(1 +, i => (2 until i).any(i % _ == 0)) | |
2.iterate[Stream](nextPrime).take(5) assert_=== Stream(2, 3, 5, 7, 11) | |
2.replicate[List](5, nextPrime) assert_=== List(2, 3, 5, 7, 11) | |
2.replicate[Option](3) assert_=== 6.some |
+>:
値を包み込み、結合する演算子。
使い方がよくわからず、 List(1).+>:(1) とか書いてたけど : がついてるとレシーバが右にくるとの御指摘が。
演算子の結合順位もよくわかっていないのでコップ本を読み直さないとですね・・・
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
1 +>: List(1) assert_=== List(1, 1) | |
1 +>: 1.some assert_=== 2.some | |
(1 +>: ((_: Int) + 1)).apply(1) assert_=== 3 |
MA
今回の関数は +>: 以外Identityに定義されています。
+>: はどこに定義されているのかというと、MAに定義されています。
MAは"型パラメータを1つとる型"Mと型Aを型パラメータにとります。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
scala> (nil[Int]: MA[List, Int]) | |
res65: scalaz.MA[List,Int] = scalaz.MAs$$anon$3@1d45221 | |
scala> (none[String]: MA[Option, String]) | |
res66: scalaz.MA[Option,String] = scalaz.MAsLow$$anon$1@90cae4 | |
Scalaではイレイジャで型M[A]の型Aが消えてしまうため、このような定義になっています。
このMAでは、"型パラメータを1つとる型"を対象にした型クラスを利用する関数が定義されています。
今後紹介する関数では、Identity,MAそしてMABで定義されたものを中心に紹介していきます。
これらはScalaz特有の関数を利用するための型クラスなので深い理解はいりませんが、Scalazを使う上で覚えておいて損はないでしょう。
1.iterate[FirstOption](identity)
返信削除わかんね(´・ω・`)