0

I want to combine 2 Scala functions into a 3rd with andThen but am running into problems with the type system.

Here is the code:

object Test{

  def process1[T](in : List[T]) : List[T] = in

  def process2[T](in : List[T]) : List[T] = in

  //this works fine but you have to read it inside out
  def combined2[T](in : List[T]) : List[T] = process2(process1(in))

  //this also works but at the cost of creating a new function every time
  def combined3[T](in : List[T]) : List[T] = {
    (process1[T] _ andThen process2[T] _)(in)
  }

  //this doesn't work. it is a function List[Nothing] => List[Nothing]
  val combined = process1 _ andThen process2 _

  def main(s : Array[String]) {
    val input : List[Int] = List(1,2,3)
    val out1 : List[Int] = process1(input)

    val combinedOut2 : List[Int] = combined2(input)

    val combinedOut3 : List[Int] = combined3(input)

    //this will not compile as combined is [List[Nothing] => List[Nothing]
    //val combinedOut : List[Int] = combined(input)
  }
}

Is there a nice way to get the value of combined to be a function from List[T] to List[T] or is this a fundamental problem with type erasure?

1

2 Answers 2

1

Not sure if it's nice, but combined3 can be shortened to:

def combined3[T] = process1[T] _ andThen process2[T] _

Creation of function instances every time may be optimized for each case:

val combinedInt = combined3[Int]

combinedInt(input)
Sign up to request clarification or add additional context in comments.

Comments

0

You can combine functions this way, it's more cleaner

implicit class FunctionCombiner[T, U](fn: T => U) {
    def &&&(f: T => U): T => U = {
        (t: T) => {
            fn(t); f(t)
        }
    }
}

After this you can run statements like:

val f1 = (i: Int) => println((1*i).toString)
val f2 = (i: Int) => println((2*i).toString)
val f3 = (i: Int) => println((3*i).toString)

val f = f1 &&& f2 &&& f3

f(5)

This produces result:

5
10
15

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.