Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

When to use Partially Applied Functions [closed]

Note: jump down to "Question" below if you just want to skip the context

When giving talks on Scala I pretty much give "toy problems" like the one below as examples of Partially Applied Functions.

def multiply(x:Int, y:Int): Int = x * y
val x5 = multiply(5, _:Int)
x5(10) //produces 50

This example does help, however it's tough for me to explain a general "this is when you'd recognize when to use a partially applied function".

Question: Anyone have their own way of successfully explaining Partially Applied Functions that really hits home for Java (or other OO language) developers?

like image 489
ThaDon Avatar asked Aug 19 '11 17:08

ThaDon


People also ask

What is partially applied function?

The Partially applied functions are the functions which are not applied on all the arguments defined by the stated function i.e, while invoking a function, we can supply some of the arguments and the left arguments are supplied when required.

What is the use of partial functions in Scala?

Solution. A partial function is a function that does not provide an answer for every possible input value it can be given. It provides an answer only for a subset of possible data, and defines the data it can handle. In Scala, a partial function can also be queried to determine if it can handle a particular value.

Does JavaScript support partial function applications?

Application in JavaScript means that a function is applied to its argument and produces a return value. So partial application also has to do with applying functions to some of their arguments. The function that is applied partially is returned to be used later.

What is partial application in Haskell?

Partial function application refers to calling a multiple parameter function with less than its total number of parameters. This results in a new function taking the remaining number of parameters.


2 Answers

Suppose you want to apply sales tax.

def withTax(cost: Float, state: String) = { /* Some complicated lookup table */ }

Now suppose you want to make a bunch of purchases in New York.

val locallyTaxed = withTax(_: Float, "NY")
val costOfApples = locallyTaxed(price("apples"))

You get maximal code reuse from the original method, yet maximal convenience for repetitive tasks by not having to specify the parameters that are (locally) always the same.

People often try to solve this with implicits instead:

def withTax(cost: Float)(implicit val state: String) = ...

Don't do it! (Not without careful consideration.) It's hard to keep track of which implicit val happens to be around at the time. With partially applied functions, you get the same savings of typing, plus you know which one you're using because you type the name every time you use it!

like image 127
Rex Kerr Avatar answered Sep 29 '22 20:09

Rex Kerr


In Java you often pass in the first (or more) arguments of a partially applied function to the constructor of a class. Rex's example might then look something like this:

class TaxProvider {
    final String state;

    TaxProvider(String state) {
        this.state = state;
    }

    double getTaxedCost(double cost) {
      return ... // look up tax for state and apply to cost
    }
}


TaxProvider locallyTaxed = new TaxProvider("NY")
double costOfApples = locallyTaxed.getTaxedCost(price("apples"))
like image 20
michid Avatar answered Sep 29 '22 19:09

michid