My aim is that after you read this article, you understand what is a functional programming. There is lot of articles for OOP, myself have return an article on OOP, but when i started learning functional programming i started loving it. Its not about OOP vs FP(functional programing) but how to take advantage of both.
What is Functional Programming?
In any program there is two core thing data and behavior. Data could be array, object,hashmap etc. Data can be in any form. Behavior is function that perform operation on data. Functional programming says that data and behavior(function) are two different thing. they should be kept separate. It simply says that you pass data to function it will process it and return new object.
There are many new terms in functional programming learning for first time will be exhaustive but my personal suggestion is that you should give this a try.
Functional programming is all about separation of concerns.It's all about packaging our code into separate chunks so that everything's is well organized in each part of our code.Functional programming says that data and behavior(function) are two different thing. they should be kept separate. The core pillar of functional programming is pure function.
What are pure function?
A function that follow below point are pure function:
- Given the same input it will provide the same output no matters how many times we call it
- It does not modify its outer world that is, it has no side effect. Let's understand with example
In above I have created two function removeLastItem and immutablyRemoveLastItem.
The removeLastItem has side effect as it modify outer world variable
arr while immutablyRemoveLastItem function has no side effect because it first copy the external variable using concat method and then alter the new array(which it has ownership of) and return it.
- Let understand with example the concept of same input then same out no matter how many time the function is called
There are some terms in functional programming let's define them
In functional programming, referential transparency is generally defined as the fact that an expression, in a program, may be replaced by its value (or anything having the same value) without changing the result of the program. This implies that methods should always return the same value for a given argument, without having any other effect.
Let's understand it with example
In the above example function
a Is referential transparent as it can be replaced by its value without effecting the result of the program while function
c is not referential transparent because here replacing with the value will effect the result of the program as function c has console.log which is one type of side effect.
A function is idempotence if for same input it provides same output or does what we expect, Idempotence is different from pure function as it allow side effect. A n example could be get api that with same input provide same output no matter how many times it is called.Another Feature of Idempotence is the idea of calling itself again and again and still the output is the same.Let see other example also:
In the above example there are three function notIdempotenceFn,idempotentFn and getAbsolute. In notIdempotenceFn function will result different output in each call so it is not idempotent while the function idempotentFn is idempotent as for same input it
will have same output that is console.log which will print the output to the console. One note idempotentFn function is not pure as it print in console that is altering the outside world. getAbsolute function is an idempotent function as it provide the same result no matter how many times i call it.
Imperative vs Declarative
Imperative code means what to do and how to do while declarative code means what to do and what need to be done it will not tell how to do it. Let's understand with an example
In the above example we have one task to
console.log 1 to 5 and how this task can be done imperatively and declaratively. The for loop is imperative because here we define what to do that is
console.log and also how to do by defining variable
let i=1, its condition
i<=5 and increment by 1
i++. The other example is
forEach loop which is declarative because here we specify what to do that is
console.log and not how to do which is manage by forEach function.
Why i am teaching you about Imperative vs Declarative because functional programming help us to be more declarative by using compose which we will learn later. compose tell our programs what to do instead of how to do it.
Immutability means not to modify original state by copying it and then applying required changes to the new state and returning the new state. Let's see an example
In above example we have two function mutatingState and immutatingState. The function mutatingState changes the orignal state while immutatingState function creates a copy of the orignal state and return new state. Functional programming recommends immutability as immutability provide stability and predictability to our code. We will come to know the importance of immutability when we understand composing.
High Order Function
What is High Order Function?
A function that receive function as an argument or a function whose return value is function,such function is a High order Function. let's see with an example
In above example we have two function hocFn and hocFn2. hocFn function return function so it is HOC while hocFn2 accept function as argument so it is also HOC.
it or passing it to another function so that we can use that variable.
I have written separate blog on closure be sure to check on that
Currying is a technique of translating a function evaluation that takes multiple parameter into evaluating multiple function that each takes a single parameter.
Let's understand with an example
In above example i have created two function multiply and currying. The multiple function takes two parameter while the currying function take single parameter at time. In this example i have tried to show how we can convert a function with multiple parameter
multiply(a,b)into multiple function with single parameter
Partial Application means we are partially applying a function. Suppose a function has 5 arguments. We want its execution to be partially that is for now i will pass 2 arguments and rest of the 3 arguments i will pass later, this is called partial application and it is possible due to closure because when we apply function partially the argument we passed are remembered and are used when we fully execute the function with remaining number of arguments. Let's understand with example.
In above example partiallyMultiplyBy5 partially apply multiply function with 5 as first argument. When executing the partiallyMultiplyBy5 function we just have to pass remaining parameter as the first argument 5 has been remember due to closure.
Memoization is a special form of caching. Memoization cache the return value of the function based on its parameter that is if the parameter does not change then the return value is memoized. let's see with an example
In above example we have two function notMemoized and memoizedFn. notMemoized function will execute the function logic of multiplication for each execution also if the parameter is same. While for memoizedFn the function logic of multiplication will only be executed if the result is not cached ,for second time with same parameter the value will return from cache.
Compose and Pipe
Composing is an idea that describe that the transformation of the data should be obvious. Let's describe compose in simple terms: if there is a data which is processed by a function and that function return new form of the data, the return data is again processed by another function which return new form of data and this chain continues until we get required output. We can say for compose that it is a design principle which describe the relationship with different components (function), here we arrange components in a assembly line which describe how the data is transformed from one function to another.
Pipe is similar to compose the difference is in execution. compose execute the components from right to left while pipe execute the component from left to write.
let see with an example
In above example i have tried to explain how we can use compose to transform the data, In the example there is requirement to multiple a number with 3 and then get absolute of the number. These are two different operation so i have created two function multiplyWith3,getAbsouleOfNum which are pure function. Now if we do not use compose then first we have to call multiplyWith3 function store it output in the variable , then use that variable to call getAbsouleOfNum function to get the desired result, this is a one way to do it. Let's now do in compose way, here we have two component(function) multiplyWith3,getAbsouleOfNum we can arrange them in a sequence in a manner that output of one program is input of another so i have created multiplyBy3andGetAbsolute function which will first execute getAbsouleOfNum and then the output of the getAbsouleOfNum function will be provided to multiplyWith3. We can also do this in the pipe way for that i have created multiplyBy3andGetAbsolutePipe here first muliplyBy3 is executed whose output is passed to getAbsouleOfNum
Arity mean number of argument the function takes. It is preferred to have less number of argument to a function to make it more usable. My preference for number of argument a function should have is 1 or 2. Let's see with an example
In above example I have created two function addNumber and getAbsoulte. addNumber function has arity of 2 as it has two argument while getAbsoulte has arity of 1 as it has one argument.
Functional programming suggests that the data and function(effect) should be separate. The function should have following properties
- Single task: A Function should be small and should perform single task
- Pure: Function should not have side effect and for same input it should provide same out
- Should have return statement.
- should be compose-able
- Immutable: Function should return a new copy of data and should not change the original state
- Should be predictable