Showing posts with label Functional Programming. Show all posts
Showing posts with label Functional Programming. Show all posts

Tuesday, June 7, 2016

What is the Difference Between Currying and Partial Application?

Currying is the act of breaking apart functions with multiple parameters into multiple one parameter functions.

Here is a simple function with multiple parameters that is not curried.
// multiple parameter function
let add x y = x + y 

Here is the same function but curried.
// curried function
let add x = 
  let addInner y = x + y 
  addInner

As you can see, the curried function is made up of another function with the first parameter baked in. Because this function is curried it can now be partially applied (you actually get this automatically with any multi parameter function in F#). Partial application is a powerful technique in functional programming if used correctly. For instance, here is a simple partial application example for the function above.
// partially applied functions
let add4 = add 4 
let add5 = add 5 

add4 1 // returns 5
add5 1 // returns 6

The add4 function partially applies the add function, which means it returns the addInner function with 'x' baked in. So the add4 function becomes:
addInner y = 4 + y

This example is trivial, how could this be used in a useful way in production code? Often in our production code we have to retrieve something from the database, like a customer, and then continue with the business operation

Business logic function:
let businessLogic (dbFun:int->Customer) customerId = 
  let customer = dbFun customerId
  // other logic

This business logic function takes as a parameter a function that retrieves a customer from the database. But the database function below needs a connection string as well (passing connection string info in makes managing connection strings easier).

Database function:
let getCustomerFromDb connectionString customerId = 
  // get customer from real database

This function has the function signature of string->int->Customer. We use partial application to turn it into an int->int so it can be used in the businessLogic function.
let customerId = 5

// partially applied get customer function
let entryPoint = businessLogic (getCustomerFromDb "RealConnection") customerId 

In a non functional language it is necessary to use dependency injection to achieve this same thing. Partial application achieves the same goal but is simpler and doesn't require extra setup code.

Saturday, February 20, 2016

Why Would I Use a Monad?

In this post I am going to describe a simple case for when to use a monad. A monad is nothing to be frightened of, it's simply a structure that describes a chain of operations. They should be embraced because if used correctly they can lead to more readable code. And, monads are easy to understand! So, let's walk through a common scenario.

We'll start out with a standard pattern I've observed in a normal C# application. Let's say there is a function that should be called, but only if a number of other validation functions first succeed. The C# code could look as follows (this code could be written better but it is just an example):
public static bool SaveRecord(int input) {
    var valid = IsGreaterThanZero(input);
    if (valid) {
        valid = IsLessThanTen(input);
    }
    if (valid) {
        valid = EqualsFour(input);
    }
    if (valid) {
        SaveRecord(input);
    }
    return valid
}
In this example we want to call SaveRecord, but only depending on the results of some other functions. Instead of branching on the valid boolean we could use exceptions, or we could put those validation calls in one line, but I'm going to argue for a better way. First let's write some code in F#. I'm a fan of Scott Wlaschin's railway programming, where program execution shortcuts if there is an error instead of using exceptions. To do this we need a type like so:
type Response =
 | Success of int
 | Failure of string
Instead of returning simple types our function inputs and outputs can be wrapped with this Response type. By using this response type our functions will have more well defined inputs and outputs which can lead to more readable programs as we will see below. So, let's re-implement the above function in F# using this response type (warning: ugly code below!):
let yuck input =
       match isGreaterThanZero input with
       | Failure f -> Failure f
       | Success a -> match isLessThanTen a with
                         | Failure f -> Failure f
                         | Success b -> match equalsFour b with
                                           | Failure f -> Failure f
                                           | Success c -> saveRecord c
As you can see that looks terrible. After every response we have to check whether not the response is valid before continuing, but luckily the language provides a way to clean it up. I'll show you step by step. First, let's create a function called bind that will help remove some duplicate logic in this function.
let bind m f =
  match m with
  | Failure f -> Failure f
  | Success a -> f a
This bind function takes a response type and a function, then simply propagates the failure if it's a failure or if it's a success it calls the function with the unwrapped value as its parameter. This serves the purpose of removing the nested match statements above and helps readability.
let withBind input =
  let result1 = bind (Success input) isGreaterThanZero
  let result2 = bind result1 isLessThanTen
  let result3 = bind result2 equalsFour
  bind result3 saveRecord
This is much more readable than the first function but we can take it a step further. We can use computation expressions in F# by building a type with the bind function we created that looks as follows:
type ValidationBuilder() =
  member this.Bind(m, f) = bind m f
  member this.Return(x) = Success x
  member this.ReturnFrom(x) = x
  member this.Zero(x) = Success x

let validation = new ValidationBuilder()
With this type we can write a function that is cleaner than before.
let withContinuation input =
  validation {
    let! result1 = isGreaterThanZero input
    let! result2 = isLessThanTen result1
    let! result3 = equalsFour result2
    return! (saveRecord result3)
  }
The computation expression allows us to build in the continuation logic so it doesn't have to be repeated everywhere in our application. The ! operator automatically calls the bind function, unwraps the value and continues on unless there is a failure in which case none of the other lines are executed. One other option we could use here is an infix operator instead of a computation expression. These can be confusing if used too often but here is how we could change the function using an infix operator.
let (>>=) m f =
  match m with
  | Failure f -> Failure f
  | Success a -> f a
The infix operator works like the bind function and when we use it in our original function this is the result.
let withInfixOperator input =
  input
  |> isGreaterThanZero
  >>= isLessThanTen
  >>= equalsFour
  >>= saveRecord
This is the most readable of all the options and shows the power of F#. See, monads aren't scary! If used correctly your programs can contain mostly program logic and are very easy to read as long as the basic concepts are well understood.

My Journey to Functional Programming

Over the last year I have transitioned from an imperative and object oriented style to a declarative and functional style of programming. Even though there was much gnashing of teeth along the way it was a worthy pursuit. I believe a declarative functional style is beneficial in a few ways I will describe below, but first I'd like to describe the journey in case you find yourself making the same transition. Last year a functional programming advocate on our team convinced us to use F# for our team's next project. What followed was a path to the dark functional side.
  1. Dismissal: I was initially skeptical about this decision as functional programming reading materials were being passed around. They stated the style was easier to read and reason about, but this did not seem so at first. The code looked mathematical and cryptic. During these initial stages it was difficult to see how these differences would make life easier as a programmer.
  2. Helplessness: Using a functional programming language for the first time felt like trying to program blindfolded without hands alone in a dark room. How do you loop? Why can't I change this record? Why is this not building!? What's a continuation? Programs that resulted from those initial iterations was a hybrid functional/object oriented style that took longer to create and didn't have a consistent feel. It wasn't until after building multiple real-world applications did it begin to sink in. Then after many tears...
  3. Bliss: It's all about the functions stupid! For my entire software engineering career building software consisted of imperative object mutation while using OO patterns as the main way of sharing code. Turning the thinking around to writing programs using mostly pure composable functional expressions was difficult, but the benefits are worth the initial struggle.
Why declarative and functional?
  • Expressiveness: Writing code in a mostly pure, declarative way using a functional language leads to easy to change, easy to understand, and testable code. If these practices are followed then it is rather easy to understand the flow of the program because most of the logic is contained in small blocks unaffected by state. Declarative code is telling you its intent (side benefit is fewer code comments) whereas imperative code tells you how.
  • Functional patterns: Many books have been written on OO patterns and a lot of those patterns are useful and elegant ways of solving specific problems. In functional programming the answer to most of these problems are to simply create more functions. With continuations and currying it's trivial to break apart functions and share code in elegant ways.
  • Interfaces: Even when using an OO style best practice is to program to the interface instead of the implementation. An interface is simply a function definition, so functional programming takes the adage to heart.
I never thought I would say it, but I'm firmly in the functional camp now and happy to be there! In later posts I will go over specific examples of why I enjoy this style.