for-comprehension returns None 如果 `for` 中的至少一个组件是 None
for-comprehension returns None if at least one component in `for` is None
我很难理解在 Scala 中使用 for-compression 的机制。
例如,如果我有
val x = for {
i <- Option(1)
j <- Option(2)
k <- Option(3)
} yield (i,j,k)
x
是 x: Option[(Int, Int, Int)] = Some((1,2,3))
。
但是,如果至少有一个组件是 None,例如
val x = for {
i <- Option(1)
j <- Option(2)
k <- None
} yield (i,j,k)
那么 x
就是 x: Option[(Int, Int, Nothing)] = None
,而我实际上希望看到类似这样的内容:x: Option[(Int, Int, Nothing)] = Some((1,2,None))
.
我查看了FAQ from Scala official documentation,其中明确指出for-comprehension
是flatmap
和map
的组合。但是我还是很难理解 x
是 None
.
我想我错过了一些关于 flatmap
和 map
区别的重要概念。
第for-comprehension"desugars"转成:
val x = Option(1).flatMap(
i => Option(2).flatMap(
j => Option(3).map(
k => (i, j, k)
)
)
)
如您所见 - 第一个选项是 flat-mapped 使用一个取其值的函数(如果它存在)和 returns 一个三元组(在第二个选项上使用类似的操作) .不管那个函数是什么——整个表达式的形式是:
val x = Option(1).flatMap(f)
现在,如果我们将 Option(1)
替换为 None
(就像您在第二个表达式中所做的那样),我们显然会得到 None
:
val x = None.flatMap(f) // None, for any f
您期望的结果 (Some((None, 2, 3))
) 不太有用 - 因为对于不同的输入,它会有 不同的类型 :它会是 (Option[Int], Int, Int)
?还是(Int, Int, Int)
?还是(Option[Int], Option[Int], Option[Int])
? (None, 2, 3)
、(1, None, 3)
和 (1, 2, None)
唯一常见的类型是 not-so-useful (Any, Any, Any)
.
我很难理解在 Scala 中使用 for-compression 的机制。 例如,如果我有
val x = for {
i <- Option(1)
j <- Option(2)
k <- Option(3)
} yield (i,j,k)
x
是 x: Option[(Int, Int, Int)] = Some((1,2,3))
。
但是,如果至少有一个组件是 None,例如
val x = for {
i <- Option(1)
j <- Option(2)
k <- None
} yield (i,j,k)
那么 x
就是 x: Option[(Int, Int, Nothing)] = None
,而我实际上希望看到类似这样的内容:x: Option[(Int, Int, Nothing)] = Some((1,2,None))
.
我查看了FAQ from Scala official documentation,其中明确指出for-comprehension
是flatmap
和map
的组合。但是我还是很难理解 x
是 None
.
我想我错过了一些关于 flatmap
和 map
区别的重要概念。
第for-comprehension"desugars"转成:
val x = Option(1).flatMap(
i => Option(2).flatMap(
j => Option(3).map(
k => (i, j, k)
)
)
)
如您所见 - 第一个选项是 flat-mapped 使用一个取其值的函数(如果它存在)和 returns 一个三元组(在第二个选项上使用类似的操作) .不管那个函数是什么——整个表达式的形式是:
val x = Option(1).flatMap(f)
现在,如果我们将 Option(1)
替换为 None
(就像您在第二个表达式中所做的那样),我们显然会得到 None
:
val x = None.flatMap(f) // None, for any f
您期望的结果 (Some((None, 2, 3))
) 不太有用 - 因为对于不同的输入,它会有 不同的类型 :它会是 (Option[Int], Int, Int)
?还是(Int, Int, Int)
?还是(Option[Int], Option[Int], Option[Int])
? (None, 2, 3)
、(1, None, 3)
和 (1, 2, None)
唯一常见的类型是 not-so-useful (Any, Any, Any)
.