我想从xml字段中获取一个数字
...
<Quantity>12</Quantity>
...
经由
Some((recipe \ "Main" \ "Quantity").text.toInt)
但有时候xml中可能没有值。该文本将为""
,并抛出java.lang.NumberFormatException。
获得Int或None的干净方法是什么?
答案 0 :(得分:63)
scala> import scala.util.Try
import scala.util.Try
scala> def tryToInt( s: String ) = Try(s.toInt).toOption
tryToInt: (s: String)Option[Int]
scala> tryToInt("123")
res0: Option[Int] = Some(123)
scala> tryToInt("")
res1: Option[Int] = None
答案 1 :(得分:10)
更多关于接受答案后使用情况的附注。在import scala.util.Try
之后,请考虑
implicit class RichOptionConvert(val s: String) extends AnyVal {
def toOptInt() = Try (s.toInt) toOption
}
或者类似的但是在一个更精细的形式中,在import java.lang.NumberFormatException
之后,仅在implicit class RichOptionConvert(val s: String) extends AnyVal {
def toOptInt() =
try {
Some(s.toInt)
} catch {
case e: NumberFormatException => None
}
}
,
"123".toOptInt
res: Option[Int] = Some(123)
Array(4,5,6).mkString.toOptInt
res: Option[Int] = Some(456)
"nan".toInt
res: Option[Int] = None
因此,
{{1}}
答案 2 :(得分:5)
这是另一种方法,不需要编写自己的函数,也可以用来升级到Either
。
scala> import util.control.Exception._
import util.control.Exception._
scala> allCatch.opt { "42".toInt }
res0: Option[Int] = Some(42)
scala> allCatch.opt { "answer".toInt }
res1: Option[Int] = None
scala> allCatch.either { "42".toInt }
res3: scala.util.Either[Throwable,Int] = Right(42)
(关于这个主题的nice blog post。)
答案 3 :(得分:4)
Scala 2.13
引入了String::toIntOption
:
"5".toIntOption // Option[Int] = Some(5)
"abc".toIntOption // Option[Int] = None
"abc".toIntOption.getOrElse(-1) // Int = -1