Why using foreach
, map
, flatMap
etc. are considered better than using get
for Scala Options? If I useisEmpty
I can call get
safely.
6 に答える
Well, it kind of comes back to "tell, don't ask". Consider these two lines:
if (opt.isDefined) println(opt.get)
// versus
opt foreach println
In the first case, you are looking inside opt
and then reacting depending on what you see. In the second case you are just telling opt
what you want done, and let it deal with it.
The first case knows too much about Option
, replicates logic internal to it, is fragile and prone to errors (it can result in run-time errors, instead of compile-time errors, if written incorrectly).
Add to that, it is not composable. If you have three options, a single for comprehension takes care of them:
for {
op1 <- opt1
op2 <- opt2
op3 <- opt3
} println(op1+op2+op3)
With if
, things start to get messy fast.
One nice reason to use foreach
is parsing something with nested options. If you have something like
val nestedOption = Some(Some(Some(1)))
for {
opt1 <- nestedOption
opt2 <- opt1
opt3 <- opt2
} println(opt3)
The console prints 1
. If you extend this to a case where you have a class that optionally stores a reference to something, which in turn stores another reference, for comprehensions allow you to avoid a giant "pyramid" of None/Some checking.
There are already excellent answers to the actual question, but for more Option
-foo you should definitely check out Tony Morris' Option Cheat Sheet.
関数を使用して実行する代わりに、、、などをmap
直接適用する方が便利な理由は、関数がどちらかで機能し、値が存在することを確認するために特別なチェックを行う必要がないためです。foreach
flatMap
Option
get
Some
None
val x: Option[Int] = foo()
val y = x.map(_+1) // works fine for None
val z = x.get + 1 // doesn't work if x is None
y
ここでの結果はです。これは、オプションの場合、同様に未定である可能性があるOption[Int]
ため、望ましいものです。は機能しないため、エラーが発生しないようにするために、多くの追加作業を行う必要があります。によって行われる追加の作業。x
y
get
None
map
Put simply:
If you need to do something (a procedure when you don't need to capture the return value of each invocation) only if the option is defined (i.e. is a
Some
): useforeach
(if you care about the results of each invocation, usemap
)If you need to do something if the option defined and something else if it's not: use
isDefined
in an if statementIf you need the value if the option is a
Some
, or a default value if it is aNone
: usegetOrElse
Trying to perform our Operations with get
is more imperative style where u need to tel what to do and how to do . In other words , we are dictating things and digging more into the Options
internals. Where as map,flatmap
are more functional way of doing things where we are say what to do but not how to do.