Functional Programming With Python

This article was created for those who want to use functional programming in their career or who are learning new programming paradigms.

We will examine the basics of functional programming and how to apply it in Python. Good readings!

Introduction to Functional Programming

Functional Programming is a popular programming paradigm closely linked to the mathematical foundations of computer science.

Python is not a functional programming language, but it supports it because it is a multi-paradigm programming language.

Since Python is a common and easy language, it is used in this article, but if you know a functional programming language, you can use it (Javascript, Haskell, Swift).

Why Do You Need Functional Programming?

Functional programming allows you to write easy-to-read codes and also provides convenience in your debugging process.

In addition, it allows you to make your codes more reliable. You can diagnose security problems more quickly.

While the effects we mentioned are very good for software, in some cases the performance of functional programming is bad.

Some Important Information For Starting

There are several terms that will be used frequently in this article, and in this section, we will examine those terms.

If the Function accesses and operates on something other than a parameter directly given to it, it is called a side-effect.

In functional programming, a function cannot access or manipulate external variables, including the input it receives, otherwise, side effects will occur.

The rules here can be bent by project, but you should try to limit them in functional programming.

Concepts For Functional Programming

Functions are the most important thing in the functional programming paradigm, but not every function is suitable for functional programming.

In this section, we will learn what to watch out for those who will be dealing with functional programming and how this affects their code.

1 – Pure Functions

The biggest rule of thumb of functional programming is that you should never manipulate the input you receive. (you should not mutate).

If you do not mutate the parameter, the readability of your code will increase. Also, since there are no side effects, you always get the same result with the same input.

Functions that do not manipulate the parameters they receive and do not use external variables are called pure functions.

# Pure Function
def double(arr):
  newArr = []
  for i in arr:
    newArr.append(i * 2)
  return newArr

# Impure Function
def double(arr):
  for i in len(arr):
    arr[i] = arr[i] * 2
  return arr

You will need separate functions for other tasks as pure functions only do 1 task. You should combine these pure functions.

You can combine pure functions by using the output produced by your first pure function as the parameter of the other function.

# First Pure Function
def increase2(arr):
  cArr = arr
  for i in range(len(cArr)):
    cArr[i] = cArr[i] + 2

  return cArr

# Second Pure Function
def getDouble(arr):
  cArr = arr
  for i in range(len(cArr)):
    cArr[i] = cArr[i] * 2
  
  return cArr

# Combine Functions
arr = [1,3,4,5,6]
val = increase2(getDouble(arr))

Thanks to the merge here, we were able to increase the elements by 2 after multiplying the array.

Pure variables have a downside: if you have a large data entry, copying it won’t perform well (don’t convert functions with big data entries to pure functions).

2 – Higher Order Functions

Let’s explain these functions simply, such functions can take another function as a parameter and return that function again.

These functions give you flexibility and give you the advantage of connecting inputs to other functions.

Also, using these functions, you can perform multiple operations on a parameter. Note that in functional programming, each function does a single task.

def display_array(arr , func):
  for i in arr:
    func(i)

arr = [1,2,3,4,5]
display_array(arr , print)

# [1,2,3,4,5]

As you can see in the example here, we keep the print function as a parameter, where the display array function is the High Order Function.

Now let’s observe with a different example why these function structures are important for the program.

# get double index of array
def double(arr):
  newArr = []
  for i in arr:
    newArr.append(i * 2)
  
  return newArr

# get triple index of array
def triple(arr):
  newArr = []
  for i in arr:
    newArr.append(i * 3)
  
  return newArr

# merge manipulated array
def merge(arr , func = double , func2 = double):
  return func(arr) + func2(arr)

print(merge([1,2,3,4] , double , triple))

# [2, 4, 6, 8, 3, 6, 9, 12]

This code will give you an advantage in debugging as there are no side effects of the functions.

The reason for using higher-order functions here is that functions after the first function use the return value of a previous function.

Python provides some useful built-in High Order Functions that make working with arrays much easier. Let’s take a look at these functions.

3 – Built-in High Order Functions

High Order Functions available in Python are much more performant than loops, and also allow you to present the code in a shorter and more concise way.

Because of these properties and being a pure function, it is very suitable for functional programming.

This section requires knowing lambda functions, if you don’t know, we recommend reading this article, you can continue later.

1 – Map Function

The map function is used to apply the desired function to each element in an iterable object, it is very short to use and returns an iterator.

As an example, let’s rewrite the function that multiplies each element by 2, which is the pure function we used at the beginning, with a map.

arr = [1,2,3,4,5,6]
newArr = map(lambda x: x * 2 , arr)

for num in newArr:
  print(num)

# 2 4 6 8 10 12

According to the function we created at the beginning, we have achieved a great increase in efficiency in terms of memory space and speed.

2 – Filter Function

The filtering function is another useful function that is used to separate the data in the feature we specify.

arr = [10,20,30,40,50]
newArr = filter(lambda x: x * 2 > 50, arr)

for num in newArr:
  print(num)

# 30 40 50

The function is easy to understand. Elements that do not satisfy the condition are not added to the variable, the condition here depends on the lambda function.

You can use these two functions in combination with each other, after all, these functions return an iterator.

# 0 to 20 numbers
nums = range(0,20)

# filter odd numbers
filterNums = filter(lambda x: x % 2 == 0 , nums)

# get double of even number
newNums = list(map(lambda x: x * 2, filterNums))

print(newNums)

# [0, 4, 8, 12, 16, 20, 24, 28, 32, 36]

To run the result returned by the Map function without loop, we have converted it into a list, now you know how to use the 2 functions together.

You can also nest functions instead of assigning them to variables, but it can be difficult to read, so it’s better to assign functions to different variables.

4 – List Comprehensions

Another feature found in functional programming languages and also found in Python is List Comprehensions.

With this feature, you can perform quick operations on lists, just like map and filter (these two features have advantages and disadvantages amongst themselves.)

# Array For Naruto Fans
names = ["sasuke","sakura","naruto","pain","madara","itachi"]

# Capitalize the first letters
trueNames = [i.capitalize() for i in names]

# Display List
print(trueNames)

# ['Sasuke', 'Sakura', 'Naruto', 'Pain', 'Madara', 'Itachi']

In accordance with functional programming, inputs do not mutate with list comprehensions. Unlike map and filter, it returns a list instead of an iterator.

nums = [1,2,3,4,5]
double = [i * i for i in nums if i > 2]

# [9 , 16 , 25]

In the example here, the loop only works on items greater than 2. Now that we have learned the necessary concepts, we can move on to the last word.

Last Word

In this article, we examined the advantages of functional programming and how it can be used with Python.

You can make your code suitable for functional programming by paying attention to the rules specified here and using structures.

Since functional programming is a rapidly growing programming paradigm, it can take you forward in the industry.

Happy Codding!

Leave a Reply

Your email address will not be published. Required fields are marked *