You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Currying decomposes a function that takes multiple arguments into a sequence of functions that each take a single argument.
14
-
Curried functions are useful since they can be used to create new functions with lower arity to perform more specialised tasks
15
-
in a concise and readable manner. This is done via partial application.
14
+
15
+
Currying decomposes a function that takes multiple arguments into a sequence of functions that each take a single argument. It helps in creating a higher-order function by partial application of its arguments.
16
16
17
17
## Explanation
18
+
18
19
Real-world example
19
-
> Consider a librarian who wants to populate their library with books. The librarian wants functions which can create
20
-
> books corresponding to specific genres and authors. Currying makes this possible by writing a curried book builder
21
-
> function and utilising partial application.
20
+
21
+
> Consider a librarian who wants to populate their library with books. The librarian wants functions which can create books corresponding to specific genres and authors. Currying makes this possible by writing a curried book builder function and utilising partial application.
22
22
23
23
In plain words
24
-
> Decompose a function that take multiple arguments into multiple functions that take a single argument.
24
+
25
+
> Decompose a function that take multiple arguments into multiple functions that take a single argument.
25
26
26
27
Wikipedia says
27
-
> Currying is the technique of converting a function that takes multiple arguments into a sequence of functions that
28
-
> each take a single argument. Given a function $f:(X \times Y) \rightarrow Z$, currying constructs a new function
29
-
> $h:X \rightarrow (Y\rightarrow Z)$. $h$ takes an argument from $X$ and returns a function which maps $Y$ to $Z$. Hence,
30
-
> $h(x)(y) = f(x, y)$.
31
28
32
-
Programmatic example
29
+
> In mathematics and computer science, currying is the technique of translating a function that takes multiple arguments into a sequence of families of functions, each taking a single argument.
However, what if we only wanted to create books from the `FANTASY` genre? We could pass in the `FANTASY` parameter on each method call; however, this is repetitive. We could define a new method specifically for creating `FANTASY` books; however, it is infeasible to create a new method for each book genre. The solution is to create a curried function.
Note that the order of the parameters is important. `genre` must come before `author`, `author` must come before `title` and so on. We must be considerate of this when writing curried functions to take full advantage of partial application. Using the above function, we can define a new function `fantasyBookFunc`, to generate `FANTASY` books as follows:
Unfortunately, the type signature of `BOOK_CREATOR` and `fantasyBookFunc` are difficult to read and understand. We can improve this by using the [builder pattern](https://java-design-patterns.com/patterns/builder/) and [functional interfaces](https://www.geeksforgeeks.org/functional-interfaces-java/#:~:text=A%20functional%20interface%20is%20an,any%20number%20of%20default%20methods).
81
+
82
+
Unfortunately, the type signature of `BOOK_CREATOR` and `fantasyBookFunc` are difficult to read and understand. We can improve this by using the [builder pattern](https://java-design-patterns.com/patterns/builder/) and [functional interfaces](https://www.geeksforgeeks.org/functional-interfaces-java/#:~:text=A%20functional%20interface%20is%20an,any%20number%20of%20default%20methods).
The semantics of the `builder` function can easily be understood. The `builder` function returns a function `AddGenre`, which adds the genre to the book. Similarity, the `AddGenre` function returns another function `AddTitle`, which adds the title to the book and so on, until the `AddPublicationDate` function returns a `Book`.
101
-
For example, we could create a `Book` as follows:
109
+
110
+
The semantics of the `builder` function can easily be understood. The `builder` function returns a function `AddGenre`, which adds the genre to the book. Similarity, the `AddGenre` function returns another function `AddTitle`, which adds the title to the book and so on, until the `AddPublicationDate` function returns a `Book`. For example, we could create a `Book` as follows:
111
+
102
112
```java
103
-
Book book=Book.builder().withGenre(Genre.FANTASY)
113
+
Book book=Book.builder().withGenre(Genre.FANTASY)
104
114
.withAuthor("Author")
105
115
.withTitle("Title")
106
-
.withPublicationDate(LocalDate.of(2000,7, 2));
116
+
.withPublicationDate(LocalDate.of(2000,7,2));
107
117
```
118
+
108
119
The below example demonstrates how partial application can be used with the `builder` function to create specialised book builder functions.
A curried function which has only been passed some of its arguments is called a partial application. Partial application
171
-
allows for the creation of functions with some pre-defined data in their scope, since partial application can be used to
172
-
create specialised functions with lower arity. This abstraction can help keep code readable and concise. Therefore, currying is useful when frequently calling functions with fixed parameters.
185
+
186
+
* When functions need to be called with some arguments preset.
187
+
* In functional programming languages or paradigms to simplify functions that take multiple arguments.
188
+
* To improve code reusability and composability by breaking down functions into simpler, unary functions.
173
189
174
190
## Known uses
175
-
Most functional programming languages support curried functions. A popular example is [Haskell](https://www.haskell.org/), in which all functions are considered curried.
191
+
192
+
* Functional programming languages like Haskell, Scala, and JavaScript.
193
+
* Event handling in UIs where a function with specific parameters needs to be triggered upon an event.
194
+
* APIs that require configuration with multiple parameters.
176
195
177
196
## Consequences
178
-
Pros
179
-
* Currying allows for partial application, which can be used to create specialised functions concisely.
180
197
181
-
Cons
182
-
* The order of the parameters in a curried function is important since we want to take advantage of partial application. It is best to input the most general parameters first and input specific parameters last.
183
-
* As shown in the programmatic example above, curried functions with several parameters have a cumbersome type signature (in Java).
198
+
Benefits:
199
+
200
+
* Increases function reusability by allowing the creation of specialized functions from more generic ones.
201
+
* Enhances code readability and maintainability by breaking complex functions into simpler, single-argument functions.
202
+
* Facilitates function composition, leading to more declarative and concise code.
203
+
204
+
Trade-offs:
205
+
206
+
* Can lead to performance overhead due to the creation of additional closures.
207
+
* May make debugging more challenging, as it introduces additional layers of function calls.
208
+
* Can be less intuitive for developers unfamiliar with functional programming concepts.
209
+
* As shown in the programmatic example above, curried functions with several parameters have a cumbersome type signature in Java.
* Function Composition: Currying is often used in conjunction with function composition to enable more readable and concise code.
214
+
*[Decorator](https://java-design-patterns.com/patterns/decorator/): While not the same, currying shares the decorator pattern's concept of wrapping functionality.
215
+
*[Factory](https://java-design-patterns.com/patterns/factory/): Currying can be used to create factory functions that produce variations of a function with certain arguments preset.
187
216
188
217
## Credits
218
+
219
+
*[Java 8 in Action: Lambdas, Streams, and functional-style programming](https://amzn.to/3J6vEaW)
220
+
*[Modern Java in Action: Lambdas, streams, functional and reactive programming](https://amzn.to/3J6vJLM)
221
+
*[Functional Programming in Java: Harnessing the Power Of Java 8 Lambda Expressions](https://amzn.to/3TKeZPD)
189
222
*[Currying in Java](https://www.baeldung.com/java-currying)
190
223
*[What Is Currying in Programming](https://towardsdatascience.com/what-is-currying-in-programming-56fd57103431#:~:text=Currying%20is%20helpful%20when%20you,concise%2C%20and%20more%20readable%20solution.)
191
224
*[Why the fudge should I use currying?](https://medium.com/dailyjs/why-the-fudge-should-i-use-currying-84e4000c8743)
0 commit comments