Reputation: 1367
I've found pretty convenient to use that in my project:
case class Thing(a: Option[String], b: Option[String], c: Option[String])
...
val a = Thing(a = Some("A"))
val b = Thing(b = Some("B"))
val c = Thing(b = Some("B"), c = Some("C"))
it actually reduce a lot of ugly None definitions and looks much readable, but now I'm wondering is there any difference from performance/implementation point of view between this and that?:
val a = Thing(Some("A"), None, None)
val b = Thing(None, Some("B"), None)
val c = Thing(None, Some("B"), Some("C"))
Thanks
Upvotes: 2
Views: 252
Reputation: 70267
Semantically, there's no difference, since None
is a singleton object. However, performance-wise, we can see what sort of code is being generated under the hood.
case class Thing(
a: Option[String] = None,
b: Option[String] = None,
c: Option[String] = None
)
object Thing {
def foo() = {
val a1 = Thing(a = Some("A"))
val b1 = Thing(b = Some("B"))
val c1 = Thing(b = Some("B"), c = Some("C"))
val a2 = Thing(Some("A"), None, None)
val b2 = Thing(None, Some("B"), None)
val c2 = Thing(None, Some("B"), Some("C"))
}
}
This is an example of the sort of thing you're asking about, I believe. We can compile this with scalac Thing.java -Xprint:jvm
to see what the Scala compiler is left with after it strips all the syntax sugar out.
val a1: Thing = new Thing(new Some("A"), Thing.apply$default$2(), Thing.apply$default$3());
val b1: Thing = {
<artifact> val x$1: Some = new Some("B");
<artifact> val x$2: Option = Thing.apply$default$1();
<artifact> val x$3: Option = Thing.apply$default$3();
new Thing(x$2, x$1, x$3)
};
val c1: Thing = {
<artifact> val x$4: Some = new Some("B");
<artifact> val x$5: Some = new Some("C");
<artifact> val x$6: Option = Thing.apply$default$1();
new Thing(x$6, x$4, x$5)
};
val a2: Thing = new Thing(new Some("A"), scala.None, scala.None);
val b2: Thing = new Thing(scala.None, new Some("B"), scala.None);
val c2: Thing = new Thing(scala.None, new Some("B"), new Some("C"));
So using the named syntax can introduce some intermediate variables. But the function call is essentially the same modulo a few bytes of stack space. More than likely, the JIT will compile these down to similarly performing snippets of code, so I'd say you have little to worry about.
Upvotes: 1