我想這個代碼片段返回我None
,而不是Some(null)
:Option.map(空)返回一些(空)
Option(x).map(x.getNullValue) // returns Some(null)
聽說Scalaz
圖書館功能來處理這種情況。那麼我怎樣才能實現我的目標:scalaz
和標準的Scala庫?
我想這個代碼片段返回我None
,而不是Some(null)
:Option.map(空)返回一些(空)
Option(x).map(x.getNullValue) // returns Some(null)
聽說Scalaz
圖書館功能來處理這種情況。那麼我怎樣才能實現我的目標:scalaz
和標準的Scala庫?
你可以與Option.apply
方法一起使用flatMap
這裏,而不是在scalaz
拉:
Option(initialValue).flatMap(x => Option(x.getNullValue))
這工作,因爲Option.apply
方法踹null
智能:
val x: String = null
Option(x) //None
Option("foo") //Some("foo")
所以,如果你知道值直接,你可以簡單地做:
Option(x.getNullValue)
您也可以使用其他方法對Option
像filter
,orElse
,或getOrElse
,根據不同的情況:
Option(initialValue).map(_.getNullValue).filter(_ != null)
Option(initialValue).orElse(Option(x.getNullValue))
Option(x.getNullValue).getOrElse(defaultValue)
我不知道scalaz,但在標準庫中你唯一的選擇真的是過濾掉null
值。 map
只是映射A => B
,並且期望B
不會是null
。
例子:
object HasNull {
def getNull: Any = null
}
scala> Option(HasNull).map(_.getNull).filter(_ != null)
res24: Option[Any] = None
或者
scala> Option(HasNull).flatMap(a => Option(a.getNull))
res25: Option[Any] = None
或者,你可以使用一個小隱魔避免Option
樣板:
implicit def toOpt[A](a: A): Option[A] = Option(a)
scala> Option(HasNull).flatMap(_.getNull)
res3: Option[Any] = None
使用flatMap
仍是關鍵,因爲它期望Option[B]
。但getNull
的類型爲B
,因此將使用隱式轉換,它將再次將可空對象包含在Option.apply
中。
正如其他人已經寫了,你可以使用flatMap來做到這一點。和一個非常類似的方法是:
case class User(name: String)
val users = List(null, User("John"), User(null))
for{
userDb <- users
user <- Option(userDb)
name <- Option(user.name)
} yield name
與None
的問題是,你不知道哪個None
您將獲得:用戶不存在或名稱?在這種情況下,scalaz可以幫助你:
for{
userDb <- users
user <- Option(userDb) \/> "No user found."
name <- Option(user.name) \/> "No name provided."
} yield name
'Option(x.getNullValue)'有什麼問題? – ipoteka
@ipoteka'x'也可以爲null,所以我也把它換成'Option' – MyTitle