Option

今日から Scala のエラーを表すデータ型を見ていく。

最初は Option 型だ。Option は言ってみれば値を1つだけ入れられるコンテナで、値の入っている Some と何もないっていないことを表す None の2つの値がある。

っていうか、これ、OCmal の Option と同じだよね。Haskell で言えば Maybe だ。

Option は、たとえば次のように作れて、動作する。

scala> val o1: Option[String] = Option("hoge")
o1: Option[String] = Some(hoge)

scala> o1.isEmpty
res0: Boolean = false

scala> o1.isDefined
res1: Boolean = true

scala> o1.get
res2: String = hoge

Option はコンテナなので型パラメータを持つ。上の例では String だ。で、持っている値は get メソッドで取得できる。

じゃあ、null を入れた場合はどうだろう。

scala> val o2: Option[String] = Option(null)
 o2: Option[String] = None

scala> o2.isEmpty
res3: Boolean = true

scala> o2.isDefined
res4: Boolean = false

scala> o2.get
java.util.NoSuchElementException: None.get
  at scala.None$.get(Option.scala:349)
  at scala.None$.get(Option.scala:347)
  … 36 elided

null を入れると Option の値としては None になる。っていうか null ってなに?Java の null?

まあいいか。とにかく中身の値がないので、get メソッドではエラーになっている。

None も Option の値なので、isEmpty とか isDefined とかのメソッドに対してはちゃんと値を返している。もうひとつ、Option には便利な getOrElse メソッドがあって None だった場合には別の値を返すことができるようになっている。

scala> o2.getOrElse("no value")
res6: String = no value

最後に、パターンマッチを見よう。

scala> val s: Option[String] = Option("hoge")
s: Option[String] = Some(hoge)

scala> val result = s match {
     |     case Some(str) => str
     |     case None => "not matched"
     | }
result: String = hoge

Option は例外と違ってふつうのデータ型なので、パターンマッチができる。例外処理を書くんではなくて、ほかのデータ型と同じような処理をかけるわけだ。