下面是一些有用的東西:
def sysValue(prop: String) = Option(System.getProperty(prop)) //returns Option[String]
def trySysValue(prop: String) = //returns Either[String, String]
sysValue(prop) map Right getOrElse Left("Absent property: " + prop)
然後你可以通過它的右投影
val batch = //batch is Either[String, (File, File)]
for {
x <- trySysValue("XDir")).right
xf <- dir(x).right
y <- trySysValue("YDir").right
yf <- dir(y).right
}
yield (xf, yf)
使用的一元Either
組合物,其中:
def dir(s: String) = { //returns Either[String, File]
val f = new File(s)
if (!f.exists()) Left("Does not exist: " + f)
else if (!f.isDir()) Left("Is not a directory: " + f)
else Right(f)
}
Either
的左側將出現錯誤消息。這個monadic組成是快速失敗。您可以使用scalazValidation
累積所有故障(例如,如果既不存在XDir
也不存在YDir
,您將看到這兩個消息)的構圖。在這種情況下,代碼應該是這樣的:
def trySysValue(prop: String) = //returns Validation[String, String]
sysValue(prop) map Success getOrElse ("Absent property: " + prop).fail
def dir(s: String) = {
val f = new File(s)
if (!f.exists())("Does not exist: " + f).fail
else if (!f.isDir()) ("Is not a directory: " + f).fail
else f.success
}
val batch = //batch is ValidationNEL[String, (File, File)]
(trySysValue("XDir")) flatMap dir).liftFailNel <|*|> (trySysValue("YDir")) flatMap dir).liftFailNel
我可以在沒有'scalaz'的情況下編碼錯誤累積嗎? – Michael
好吧,如果你通過自己的圖書館引入相同的概念,你可以。你正在尋找的是**應用函子**和** monoids **的組合。但是,這些非常有用和普遍,你可能只是使用scalaz。 –
我在這裏談論它們:http://skillsmatter.com/podcast/scala/practical-scalaz-2518 –