Ivan
Ivan

Reputation: 38

Scala function consume and return the same upper-bound type

Consider the following:

  sealed trait IntTree
  case class Leaf(value: Int) extends IntTree
  case class Branch(left: IntTree, value: Int, right : IntTree)
  
  def test[A <: IntTree](x: A): A = {
    x match {
      case Leaf(v) => Leaf(v)
      case Branch(l, v, r) => Branch(l, v, r)
    }
  }

In the function test, I have the upper-bound parameter A <: IntTree
I'd like to get it to work like the following:

test(Leaf(1)) // must return Leaf
test(Branch(Leaf(1), 1, Leaf(2))) // must return Branch

val tree: IntTree = Branch(Leaf(1), 1, Leaf(2))
test(tree) // must return IntTree

Though, it does not compile
Like, it's unable to prove that the created Leaf and Branch inside of the pattern matching is actually of type A
Is it possible to express it without the runtime casts?

The best solution I've found so far is:

def test[A <: IntTree](x: A): A = {
  x match {
    case Leaf(v) => Leaf(v).asInstanceOf[A]
    case Branch(l, v, r) => Branch(l, v, r).asInstanceOf[A]
  }
}

Not elegant but working

Upvotes: 0

Views: 50

Answers (0)

Related Questions