1. 什么是Option类型
Option是Scala 提供的一种数据类型,表示 可选值类型
它只有两个实例
Some(x),其中 x 表示实际的值
None对象,代表没有值
2. 封装数据与拆解数据
2.1 封装数据
当var有值时 : Some(var)
当var为null时 : None
test("将 字符串变量 封装到Option类型中") {
val x: Option[String] = Some("小明")
val y: Option[String] = None
val x1: Option[String] = Option("小明")
val y1: Option[String] = Option(null)
/*
* Option("小明") 调用的是 Option伴生对象的 apply方法
* def apply[A](x: A): Option[A] = if (x == null) None else Some(x)
* 实际还是 用 None 和 Some对象 来复制
* */
}
2.2 拆解数据
方式1: 直接获取 Some中的值(不推荐)
test("将 字符串 从Option对象中拆解处理") {
val x: Option[String] = Some("小明")
val y: Option[String] = None
// TODO 方式1: 直接获取 Some中的值(不推荐)
/*
* 不推荐原因
* 当Option对象为 None时
* 会抛出 java.util.NoSuchElementException: None.get
* 代码健壮性太差,所以不推荐
*
* */
println(x.get)
println(y.get)
}
方式2: 通过getOrElse方法获取值(推荐)
test("将 字符串 从Option对象中拆解处理") {
val x: Option[String] = Some("小明")
val y: Option[String] = None
// TODO 方式2: 通过getOrElse方法获取值(推荐)
/*
* 推荐理由:
* 当Option对象为 None时
* 会使用指定的 默认值
* */
println(x.getOrElse("nameless"))
println(y.getOrElse("nameless"))
}
方式3: 通过模式匹配来获取值(推荐)
test("将 字符串 从Option对象中拆解处理") {
val x: Option[String] = Some("小明")
val y: Option[String] = None
// TODO 方式3: 通过模式匹配来获取值(推荐)
def getString(s: Option[String]): String = s match {
case Some(s) => s
case None => "nameless"
}
println(getString(x))
println(getString(y))
}
3. Option类型使用场景
在我们开发程序的时候,有时候会忘记判断变量为null,而导致运行时出现 NullPointerException异常 Option类型 就是强制要求我们对变量做判断,来避免变量为null的情况,通过这种方式来增强代码健壮性
3.1 遍历Map
object GetValueByKey extends App {
val map: Map[String, String] = Map("id" -> "1", "name" -> "奉先")
private val op1: Option[String] = map.get("id")
private val op2: Option[String] = map.get("id1")
//通过 key 获取value的值(key不存在时,获取默认值)
println(op1.getOrElse("default")) //1
println(map.get("name").getOrElse("default")) // 奉先
println(map.getOrElse("no", "default")) //default
}
3.2 优雅的处理方法中null
// 不处理 null 值
def getString(x: String) = {
println(s"${x} 是否a开头: ${x.startsWith("a")}")
}
getString("abc") // abc 是否a开头: true
getString(null) // java.lang.NullPointerException
// 使用 Option 优雅的处理 null值
def getString(x: String) = {
println(s"${x} 是否a开头: ${Option(x).getOrElse("999").startsWith("a")}")
}
getString("abc")
getString(null)