Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Combining wrapped elements in Scala: Option[Array[Int]]

Tags:

scala

I'm trying to combine to arrays that are wrapped in an Option:

val a = Option(Array(1, 2, 3))
val b = Option(Array(4,5))
val q = for {
  x <- a
  y <- b
} yield x ++ y

The problem is that if b is None it returns None even though I'd like to have a. And if a is None the compiler complains that ++ is not a member of Nothing (even though I expect to receive b). Is this doable with the standard library or do I have to look at semigroups in Cats or Scalaz?

I tried the following in Cats but couldn't get it to work:

Semigroup[Option[Array[Int]]].combine(a,b) // === a |+| b

It tells me that:

could not find implicit value for parameter ev: cats.kernel.Semigroup[Option[Array[Int]]]

The resulting type should be the same as the types of a and b.

like image 819
Ian Avatar asked Dec 01 '25 17:12

Ian


2 Answers

(a ++ b).flatten.toArray

The ++ method is not a part of the Option class, but it works here because of an implicit conversion. If you see the scala doc for Option, it says This member is added by an implicit conversion from Option[A] to Iterable[A] performed by method option2Iterable in scala.Option.

So, options can be treated as iterables.

like image 58
Samar Avatar answered Dec 04 '25 06:12

Samar


Preserving the type Option[C[X]], where C is some collection type and X is the element type of that collection, I came up with:

a.fold(b)(x => b.fold(a)(y => Option(x ++ y)))
like image 26
jwvh Avatar answered Dec 04 '25 06:12

jwvh



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!