我知道在Scala中,一个方法永远不应该返回null
...但是输入参数是什么?给出以下代码片段......
object MyObject {
def myMethod(p: String): Option[String] = {
if (p == null) throw new IllegalArgumentException("p is null.")
...
}
}
...我检查p
的方式是否正确?有什么建议吗?
答案 0 :(得分:23)
惯例是Scala代码不使用空值(具有少量异常,在使用这些库函数时应立即修复)。
因此,Scala中的null表示某些内容出错(至少是PBCAK),因此您也可以抛出异常。这不是常规操作;这是严重搞砸的事情。无论何时遇到严重的搞砸,都要抓住例外。捕获IllegalArgumentException
而不是NullPointerException
不会增加额外信息。只留下原件。
如果代码来自Java,那么处理它的规范方法是将其包装在Option
中,这会将null
转换为None
。那你甚至可能不需要抛出异常;只需返回None
。
def myMethod(p: String) = Option(p).map(_.toLowerCase)
如果在null时无法继续,那么您需要考虑信息性异常是否有用。 Option(p).orElse(throw new IllegalArgumentException("Null!"))
是表达异常抛出情绪的一种紧凑方式。
在Scala 2.10中,您还可以在scala.util.Try(...)
中包装内容,它会自动为您捕获并打包异常。如果你想要一个打包的异常而不是一个抛出的异常,这就是你要走的路。 (并使用Try
代替Option
。)
import scala.util.Try
def myMethod(p: String) = Try(p.toLowerCase)
最后,对于替代结果的更一般处理,请使用Either
。错误处理的惯例是预期输出为Right(whatever)
,而Left(whatever)
表示出现问题。
答案 1 :(得分:6)
有几种方式,你的方式就是一种。
你也可以使用:
require(p != null, "p is null.")
或“更实用”的方式是使用Option
:
def myMethod(p: String): Option[String] = {
// no exception
for {
pp <- Option(p)
} yield p + " foo bar"
}
编辑:
或者如果您想要在没有抛出异常的情况下发生错误,可以使用Either
:
def myMethod(p: String): Either[Exception, String] = {
if(p == null) Left(new IllegalArgumentException("p is null."))
else Right(p + "foo bar")
}
答案 2 :(得分:0)
Scala成语基本上是“不要永远使用空值”。因此,除非您正在编写需要容纳肮脏Java用户的API,否则我不会担心它。否则,您将最终为每个编写的方法插入此样板检查。
你美丽的单行方法
def square(x: String): String = math.pow(x.toInt, 2).toInt.toString
会变成像
这样尴尬的东西def square(x: String): String =
if (x == null) throw new NullPointerException()
math.pow(x.toInt, 2).toInt.toString
}
或
def square(x: String): String = Option(x) match {
case Some(x) => math.pow(x.toInt, 2).toInt.toString
case None => throw new NullPointerException()
}
多么可怕。
答案 3 :(得分:0)
我最喜欢的方法是:
object HandlingInputValidation {
def main(args: Array[String]) = {
println("A1: " + handleInput("Correct ") + " END")
println("A2: " + handleInput("Correct") + " END")
println("A3: " + handleInput("") + " END")
println("A4: " + handleInput(" ") + " END")
println("A5: " + handleInput(null) + " END")
}
def handleInput(data: String): Option[String] = {
Option(data).map(_.trim.toLowerCase)
}
}
在这种情况下,null
将为None
,并且会修剪空格。