What is the Difference Between Function Literal and Values in Scala

Function Literal vs Function Values

I encountered some bug a couple of weeks ago when trying to play around with partially applied function.

Partial Applied Function is a function that partially created, leaving some of the arguments not applied. While you invoke the function, you can state some of the arguments, and the left argument is supplied when it is required.

Take this for an example:

def add(a: Int, b: Int): Int = a + b 

val addition = add _

addition(1,2) // 3

However, when I try to do it in function literal:

val add = (a:Int,b:Int) => a+b
// add: (Int, Int) => Int = $$Lambda$844/1630986748@1736c1e4

val addition = add _
// addition: () => (Int, Int) => Int = $$Lambda$845/1518517336@4aab7195

addition(1,2) // this doesn't work

addition()(1,2) // 3

Makes we wonder the difference between function literal and function value.

In the scala book, the definition of function literal and function value is at the compile and run time.

For function literal, (anonymous function or val function), will be compiled into Function2 trait under the hood. Usually, they snap it with an apply method that also is run as a def function (value function).

Therefore, if you assign to a val as an anonymous function, the scala will transform it into a singleton object that has a function apply.

final class anonFun extends scala.runtime.AbstractFunction2 {
    final def apply(a: Int, b:Int) = a + b
}

val add = new anonFun();

When you assign the function literal to another variable as a, the variable will also be created with another object that has another apply method - causing it becoming a higher-order function () => () => something.

However, function values, def function, in scala is served as a regular method in Java. Therefore, when you write def and assigned it to another variable, that variable is getting the method that has access to other members variable in that class. Therefore, the compiler does not create a Function2 trait and an apply method.

It creates an instance method of the object

package <empty> {
  object Main extends Object {
    def add(a: Int, b:Int): Int = a.+(b);
    def <init>(): Main.type = {
      Main.super.<init>();
      ()
    }
  }
}

Main Takeaway:

  • Function literal, val function, is compiled into a class when instantiated at run-time is a function value. It becomes the object itself.
  • If you assign another variable as a partially applied function to a function literal, it created another object literals that have an apply method slap into it. Therefore, creating a higher-order function.
  • If you use function value, a def function compiles into a method in Java. Therefore, it becomes an instance method of an object.

Like this Article?

Sign up for my newsletter to get notified for new articles!


Related Posts

5 Anti Pattern for Writing Code in a Functional Programming Language

No 1. Nested Asynchronous Function

Will the Newest Generation of Programmers End Up Taking Older Software Engineers Jobs since they are Younger and know the Latest Technology

Will I lose my Job To the Younger Generation if I am not Passionate about Technology

Use This Mantra to Decide whether You Want to go to Big Tech or a Startup

If you want to Go Deep, Go for Big Tech. If you want to Go Wide, Go for Startup.

Why Do Functional Programmers Prefer For-Comprehension Over Imperative Code Block

Short Answer - Readability

Does Seniority Title Really Matters in Tech

The answer is always - depends