DEV Community

loading...
Cover image for CodeWars assignment that got me thinking – the power of lambda!

CodeWars assignment that got me thinking – the power of lambda!

Jelena
Python Developer Let's connect and build things!
・4 min read

If you didn’t know about the CodeWars – go check it out.
It is a great place to practice and gain new knowledge because some assignments may cause you headaches. Especially if you are not an experienced developer.
Not because assignments are ultra-hard, but because, as someone who doesn’t have a lot of experience, you also need to learn what and where to look for.
For me, one of such cases was the following assignment (kata):

Let's have a look at some examples:

seven(times(five())) # must return 35
four(plus(nine())) # must return 13
eight(minus(three())) # must return 5
six(divided_by(two())) # must return 3
Requirements:

There must be a function for each number from 0 ("zero") to 9 ("nine").
There must be a function for each of the following mathematical operations:
plus, minus, times, dividedBy (divided_by in Ruby and Python).
Each calculation consist of exactly one operation and two numbers.
The most outer function represents the left operand, the most inner function represents the right operand.
Division should be integer division. For example, this should return 2, not 2.666666: eight(divided_by(three()))

At the first glance, the assignment looked easy, but...I’ve tried to solve this assignment for several hours – no luck. Had to check the discussion on the page so I could find the hint to a solution.

What is lambda and how we can implement it here?

Lambda function is a small and anonymous function.
It is a one-statement function that returns something, but return keyword is implied and it is actually not shown in the construction of the lambda function.
Let's compare the regular and lambda function:

def regular_function(number):
    return number

lambda_function = lambda number: number

print(regular_function(7))
print(lambda_function(8))

>>> 7
>>> 8
Enter fullscreen mode Exit fullscreen mode

Lambda can have many arguments, yet it can only have one expression.

Syntax of a lambda:
lambda arguments: expression

multiply = lambda x, y: x * y
print(multiply(2, 5)) # prints 10

add = lambda x, y: x + y
print(add(6, 5)) # prints 11
Enter fullscreen mode Exit fullscreen mode

When you look at these examples, you can’t see the advantage of lambda functions compared to regular functions.

That’s why the best usage of lambda is when you use it as an anonymous function inside of another function.

We will explain this on the CodeWars assignment from the beginning of the post.
For example, five(times(three())) needs to return 15: times() needs to take 5 (from five()) and 3 (from three()), multiply them and return 15.

Based on this, five() should return 5 and three() should return 3. But, both of these functions should have the possibility to take another function as an argument (in this particular case – times()).
In case that five() has no function as an argument, it should return 5. In case it has function as an argument, it should be able to return that function and use 5 as an argument.
Now we will write a universal function that will be used in five(), three(), and other functions where numbers from 0 to 9 are defined. We will use numbers.py file:

def universal_function(number, func=None):
   if func:
      return func(number)
   else:
      return number

def five(func=None):
   return universal_function(5, func)
Enter fullscreen mode Exit fullscreen mode

What does universal_function() do? If func is provided as an argument, it will use the number as a parameter in a provided func.
If func is not provided, it will return just a number.

Let’s now add code for three(), which is basically the same as a code for five():

def three(func=None):
   return universal_function(3, func)

Enter fullscreen mode Exit fullscreen mode

Now, we need to write function for calculation – times(). Here we will use lambda!
Based on the assignment, five(times(three())) should return 15. So times() needs to take the numbers from three() and five().
Let's add this to numbers.py:

def times(x):
   return lambda y: y * x
Enter fullscreen mode Exit fullscreen mode

The assignment says: The most outer function represents the left operand, the most inner function represents the right operand.

So x is coming from three() and y is coming from five().
Now we will break this:
three() is the most inner function and returns only number 3, which is x.
five() is the most outer function and returns 5 and func, which is provided as an argument.

In other words: five(5, function=times()). 5 is y, and times() multiplies 5 and 3, so the result is 15.

Similarly, we will write the code for other numbers and calculations.
Let's finalize the numbers.py:

def universal_function(number, func = None):
   if func:
      return func(number)
   else:
      return number

# Numbers
def zero(func=None): 
   return universal_function(0, func)

def one(func=None): 
   return universal_function(1, func)

def two(func=None): 
   return universal_function(2, func)

def three(func=None): 
   return universal_function(3, func)

def four(func=None): 
   return universal_function(4, func)

def five(func=None): 
   return universal_function(5, func)

def six(func=None): 
   return universal_function(6, func)

def seven(func=None): 
   return universal_function(7, func)

def eight(func=None): 
   return universal_function(8, func)

def nine(func=None): 
   return universal_function(9, func)

# Calculations
def times(x): return lambda y: y * x
def divided_by(x): return lambda y: y/x
def plus(x): return lambda y: y + x
def minus(x): return lambda y: y - x
Enter fullscreen mode Exit fullscreen mode

Side note:
If you haven’t tried CodeWars, do it. Pretty cool way to learn new things and rewire your brain.

Discussion (2)

Collapse
hanpari profile image
Pavel Morava

For this particular assignment, you may want to check partial from functools and module operator, both from standard library.

For studying Python, I keep recommending checkio.org. From my experience, from discussions under solved task there, one can obtain beneficial insight from many experts.

They have even category for extravagant solutions, called creative, where the most unexpected approaches can be find.

You can even use Numpy and other non-standard libraries there which is very seldom case on other coding sites.

Hope it helps.

Collapse
joks84 profile image
Jelena Author

Hi Pavel! Thank you so much for the feedback and suggestions, I appreciate it.
I already went through some of the things you mentioned.
And you got me intrigued with the ckeckio.org - will check that for sure!