SlideShare a Scribd company logo
Scalaz
– とある型クラスのライブラリ-
     水島 宏太
     (@kmizu)
自己紹介
の前に
発表途中でも遠慮無く
(突っ込んで/質問)ください
@kmizu http://twitter.com/kmizu
          id:kmizushima
http://d.hatena.ne.jp/kmizushima
          他称 Scala Bot
去年まで大学院生(博士課程)
ブログで就活⇒今の会社に就職
   運が良かった?
まだまだ新米
Scalaエヴァンジェリスト(笑)
Scalazについて話します
その前に
ちょっと待って
Scalazって何?
頭のおかしい(褒め言葉)
凄い人たちが作ったライブラリ
Scalaz
型クラス(Type Classes)
純粋関数型データ構造
(Pure Functional Data Structures)
最低限の依存関係
(J2SE + Scala標準ライブラリ)
IntelliJ IDEA使って開発してる
なんだか難しそう?
コード例
Scalaz
☆って何だよ☆って
Scalaz
★って何だよ★って
数学記号ならわかる
何故☆★?
あちこちでUnicode文字を
   使いまくり
向こうの人はどうやって入
   力しているのか
それが知りたい
ここから真面目に紹介
Scalaz
http://code.google.com/p/scalaz/
Scalaの標準ライブラリに
  無いあれこれを集めた
    便利ライブラリ
パッケージ一覧
scalaz ←自分が紹介
scalaz.effect
↑@halcat0x15aさんが紹介
scalaz.concurrent
scalaz.io
scalaz.http      ググってください



scalaz.geo
scalaz.scalacheck
scalazパッケージ
Scalazのコア
色々なtrait/class
  の集まり
中心は
便利な型クラス &
 それを利用した
  ライブラリ
純粋関数型データ構造
 (不変データ構造)
   ライブラリ
Category
Applicative
  Functor
   Arrow
   Kleisi
   Monoid
   Monad
    ...
IOモナドまである
# Scalaで必要なのか…?
どういうバックグラウンド
   の人が作ったか
    よくわかる
でも、この辺の用語は
 わからなくてもOK
便利なとこだけ使おう
基本的な命名規約
とかコーディングルール
末尾にs
        ↓
implicit conversion
  を提供するtrait
末尾にW
         ↓
 implicit conversion
によって拡張するための型
 PimpedType[T]を継承
わかりやすい例
scalaz.BooleanW
scalaz.Booleans
Boolean型に
便利?メソッドを追加
二つ揃って一人前
いいからコードを
import scalaz._
    import Scalaz._

       var i = 1
 i < 3 ∧ i > 0     true
i < 1 ∨ i == 1      true
 i == 1 when { i+= 1 }
 (i < 3).guard[List](1)
i != 2 unless { i+= 1 }
          ...
import scalaz._
import Scalaz._
この二行だけで使える
他のをimportしなくていい
次
scalaz.Options
scalaz.OptionW
Option型に
便利?メソッドを追加
(ry
val i: Option[Int] = Some(100)
val j: Option[Int] = None
val k: Option[Double] = Some(50.0)
val l: Option[Double] = None
i.orZero    100
j.orZero    0
k.orZero    50.0
l.orZero    0.0
i.orEmpty[List]    List(100)
j.orEmpty[List]    List()
k.orEmpty[Vector]    Vector(100)
l.orEmpty[Vector]    Vector()
i | 200    100
j | 200    200
...
次
scalaz.Lists
scalaz.Listw
List型に
便利?メソッドを追加
import scalaz._
import Scalaz._
val lst = List(1, 2, 3)
lst.toNel    Some(NonEmptyList(1, 2, 3))
lst.powerset    List(List(1, 2, 3), List(1, 2), ...)
lst.filterM{x => Set(x < 3)}      Set(List(1, 2))
lst.filterM{x => Set(x < 2)}      Set(List(1))
lst.tails.toList    List(List(1, 2, 3), ...,List())
NonEmptyList ?
その名の通り
空(Nil)でない事が保証さ
     れているList
   (のようなもの)
⇒ head, tail が必ず
  成功する
  reduceLeft,
  reduceRightも同様
型安全性にとって重要
ところで
型クラスの話はどこ?
それは皆様の心の中に
というわけではなく
既に使っています
val i: Option[Int] = Some(100)
val j: Option[Int] = None
val k: Option[Double] = Some(50.0)
val l: Option[Double] = None
i.orZero    100
j.orZero    0
k.orZero    50.0
l.orZero    0.0
i.orEmpty[List]    List(100)
j.orEmpty[List]    List()
k.orEmpty[Vector]    Vector(100)
l.orEmpty[Vector]    Vector()
i | 200    100
j | 200    200
...
0相当の値(零元)を取得
型毎に「零」値は異なる
そもそも「零」が無い型も
どうやって「零」を取得?
というわけで
orZeroの定義を見る
Zero[A
                               [A]):
  def unary_~(implicit z: Zero[A]): A =
        value getOrElse z.zero
                       Zero[A
                           [A]):
def orZero(implicit z: Zero[A]): A = ~this
Zero[Z]
零元を取得するためだけの
   trait(型クラス)
trait Zero[Z] { val zero: Z }
ちょーシンプル
でも重要
色々な型クラス
Zero
  Equal
 Length
Semigroup
   ...
最初出てきた
Category
Applicative
  Functor
   Arrow
   Kleisi
   Monoid
   Monad
    ...
こいつらも型クラス
純粋関数型データ構造
要はimmutableな
 データ構造
scala.collection.
immutableにあるようなの
immutableデータは効率が
         悪い?
必ずしもそうではない
でもその話は置いておく
Scalazが提供する
純粋関数型データ構造
Zipper
FingerTree
  + Rope
あんまり多く無い
標準コレクション
が充実してるせい(たぶん)
Zipper
一言で言うと
純粋関数型イテレータ
 要素更新もO(1)で
  できるよ!
とりあえずコードを(ry
val list = List(1,2,3)
val zipper = list.toZipper.get.tryNext
val updated = zipper.insert(10).insert(20)
updated.toStream.toList // List(1,2,10,20,3)
とりあえずコードを(ry
FingerTree
一言で言うと
cons, reverse, cdr: O(1)
 append, split: O(log n)
     ※償却計算量
例は省略
他にも色々ある
でも時間が
というわけでひとまず終了
ご静聴
ありがとうございました
質問タイム?

More Related Content

Scalaz