A popular interview topic for web developers is explaining functional programming versus object-oriented programming. Don’t know what we’re talking about, or are you looking for a little refresher? Look no further.
Functional programming (FP) and object-oriented programming (OOP) are two different programming paradigms. That is, a way of thinking about writing software based around certain principles.
A paradigm is a set of programming habits that constrain you in some way. This might sound negative, but these trade-offs aim to help limit bugs and mistakes.
- What is functional programming?
- What is object-oriented programming?
- Functional programming vs OOP: Pros and cons
- Final thoughts
1. What is functional programming?
The obvious answer is that functional programming centers around functions. Sounds simple, but what does this actually mean? Essentially, it involves taking inputs and getting outputs. Functional programming has two key concepts.
- Pure functions
- Avoids shared state and mutable data
We mentioned functional programming is focused on building software based around pure functions. Now let’s break that down.
First, a function is a process that takes some input, called arguments, and returns a value. A pure function has additional criteria:
- Given the same input, always return the same output
- No side effects
For example, take the function
Math.random(); // => 0.6011236482846291
Math.random(); // => 0.8002747611174926
Math.random(); // => 0.5488561222294628
Even though there are no arguments passed into
Math.random(), it returns a different output every time. This means the function is not pure.
Here is an example of a pure function:
const multiplyByTwo (number) => number * 2;
multiplyByTwo(5); // => 10
multiplyByTwo(5); // => 10
Every time you run the
multiplyByTwo function with the argument of 5, it will return 10. It also does not rely on any external mutable state elsewhere in the application. This makes it a pure function.
Shared state and mutable data
Once your program grows, it starts to involve many different functions and objects. This is where state comes in. State is a way to create more structure around the status of your code.
State keeps track of the status of your entire application, or of an individual object. For example, if a user has changed the language of the web page, we store this in state. Filters in use during online shopping, current page number or page size, can all be stored in the state.
Shared state is any data that exists in a shared scope, i.e. where values or functions are accessed. A function has its own functional scope (what’s in the function). Pure functions don’t use state outside their own scope.
Functional programming avoids shared state. The philosophy behind this is that shared state requires more research. It takes more energy to avoid negative side effects elsewhere in the application. You need to know the history of every shared variable that the function uses when it’s not pure. This is why pure functions avoid shared state and only rely on data within their own scope.
Mutable data is any data that can be changed once it’s created. Like shared state, functional programming avoids mutable data. Mutable data makes it easier to create side effects elsewhere in the application. In short, it means you’re more likely to introduce bugs to your app.
Examples of side effects are:
- Modifying any external variable or object property,
- Logging to the console
- Setting off any external process
- Calling any other functions with side effects
Examples of functional programming languages
Some common functional programming languages are Haskell, Clojure, and Erlang.
2. What is object-oriented programming?
Object-oriented programming focuses on classes and objects, rather than functions and logic. With OOP, both data and its functionality are grouped together. The structure of OOP includes classes, objects, methods, and attributes.
Objects are specific instances of a class. Say you have a class
Dog, for example. The dog class can be used to create an object,
goldenRetriever. This object has unique values for the properties defined in the class.
Methods are functions that are defined with the class and are only available to objects of that type.
Attributes are characteristics of the class that differentiate it from other classes. If our class is
Dog, for example, these could be things like
One way to think about attributes is as the noun or adjective of a class, while methods are the verb. One can have many entities inheriting from the same class but holding different data.
Key concepts of object-oriented programming:
Encapsulation encloses an object’s methods and properties within the object. The benefit of this is to not expose them. An example would be API extraction, i.e. controlling which methods and data you allow others to use.
This control helps with race conditions. A race condition occurs when two or more threads can access shared data and try to change it at the same time. This can cause bugs by leading to unpredictable results.
Abstraction hides the complex implementation details and only shows the functionality to users.
For example, you may make a class for
Person, and the person has a family and a job.
Job can be abstracted to different classes.
Each class handles only that functionality. This groups the data with its related functionality. Abstraction makes it easier to handle complexity by splitting it into smaller parts.
Inheritance allows the parent class to pass functionality to the child class using the
extends keyword. This helps make the code reusable rather than writing the same code over and over.
With inheritance there is a parent class and a child class. The child class inherits the methods and attributes from the parent class. It can also have its own properties and methods.
A major benefit of inheritance is reusability. Rather than write code from scratch for your
goldenRetriever object and your
corgi object, they can both inherit from your
Polymorphism is the ability of a variable, function or object to take on different forms.
In OOP, it’s when you can treat an object as a generic version of something. When you access it, the code determines which exact type it is and calls the associated code.
So you could give a class
Shape and a method
draw(). When calling
Shape.draw(), you’ll get the correct behavior for the specific shape.
Polymorphism lets us modularize our system by handling different modules in consistent ways. This makes the code more reusable. We don’t have to write separate functions like
Examples of OOP languages
Functional programming vs OOP: Pros and cons
Is one paradigm better than the other? Well, like everything…it depends.
Functional programming is better if you have a fixed set of things and you need to add operations to them. Adding functions that perform calculations on existing data types is one example of this.
OOP works well when you have a fixed set of operations on things, and you need to add more things. Here you add new classes that implement existing methods. The existing classes are left to themselves.
Functional programming leads to reliable results without side effects. It returns what you expect, and has an emphasis on efficiency and optimization. FP uses a declarative style. Programs describe their desired results without explicitly listing commands or steps that must be performed. The downside is that it can be harder to read due to the very large number of functions.
OOP is very understandable and readable. It uses an imperative style, which is like a simple set of instructions. The downside is it can have unpredictable results. You’re more likely to have side effects due to multiple threads accessing a common resource.
For more of a visual display of some of the big differences between too, this infographic will help:
4. Final Thoughts
As you can see from this introductory guide to what they’re all about, it’s obvious that both OOP and FP are big web development topics in themselves. As a developer, it’s good to understand the basics of each, the differences between them and their use cases.
Object-oriented programming versus functional programming is a controversial topic in the developer community. Engineers tend to swear by one or the other. In reality, both have their benefits and trade offs. Whichever side you’re on, there is something to be learned from both paradigms.
If you’d like to read more about the world of web development, have a look at these articles: