Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add materials for functional programming update #561

Merged
merged 3 commits into from
Jul 31, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 23 additions & 0 deletions functional-programming-python/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# Functional Programming in Python: When and How to Use It

This folder contains the sample code used in the RealPython tutorial [Functional Programming in Python: When and How to Use It](https://realpython.com/python-functional-programming/).

## Run the Scrips

You can run the individual files as Python scripts:

```sh
$ python file_name.py
```

You'll see some output printed to your terminal.

For more context, please read the associated tutorial.

## About the Author

Martin Breuss - Email: martin@realpython.com

## License

Distributed under the MIT license. See ``LICENSE`` for more information.
37 changes: 37 additions & 0 deletions functional-programming-python/filter_iterables.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
"""
Example use cases of Python's `filter()` function.
"""


# Keep only high numbers.
def greater_than_100(x):
return x > 100


print(list(filter(greater_than_100, [1, 111, 2, 222, 3, 333])))
print(list(filter(lambda x: x > 100, [1, 111, 2, 222, 3, 333])))


# Filter out odd numbers.
def is_even(x):
return x % 2 == 0


print(list(filter(is_even, range(10))))
print(list(filter(lambda x: x % 2 == 0, range(10))))

# Keep only uppercase strings.
animals = ["cat", "Cat", "CAT", "dog", "Dog", "DOG", "emu", "Emu", "EMU"]


def all_caps(s):
return s.isupper()


print(list(filter(all_caps, animals)))
print(list(filter(lambda s: s.isupper(), animals)))

# Remove empty strings.
animals_and_empty_strings = ["", "cat", "dog", "", ""]

print(list(filter(lambda s: s, animals_and_empty_strings)))
18 changes: 18 additions & 0 deletions functional-programming-python/function_scopes.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
"""
Example of a nested function scope.
"""


def outer():
def inner():
print("I am function inner()!")

# Function outer() returns function inner().
return inner


function = outer()

print(function)
print(function())
print(outer()())
22 changes: 22 additions & 0 deletions functional-programming-python/functions_as_arguments.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
Examples of using a function object as an argument.
"""

animals = ["ferret", "vole", "dog", "gecko"]
print(sorted(animals))

animals = ["ferret", "vole", "dog", "gecko"]
print(sorted(animals, key=len))

animals = ["ferret", "vole", "dog", "gecko"]
print(sorted(animals, key=len, reverse=True))


def reverse_len(s):
return -len(s)


print(sorted(animals, key=reverse_len))

# Using a lambda expression
sorted(animals, key=lambda s: -len(s))
42 changes: 42 additions & 0 deletions functional-programming-python/functions_overview.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
"""
Examples of using functions as objects.
"""


# Call a function.
def func():
print("I am function func()!")


print(func())


# Assign it to a new name.
another_name = func
another_name()

# Show a string representation of a function object.
print("cat", func, 42)

# Access a function object in a list.
objects = ["cat", func, 42]
objects[1]

print(objects[1]())

# Use a function object as a key in a dictionary.
# Note that this is probably not a good idea.
d = {"cat": 1, func: 2, 42: 3}
print(d[func])


# Pass a function as an argument.
def inner():
print("I am function inner()!")


def outer(function):
function()


print(outer(inner))
46 changes: 46 additions & 0 deletions functional-programming-python/higher_order_reduce.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
"""
Example implementations of using `reduce()` to create
functional versions of `map()` and `filter()`.
"""

# Compare `map()` to `custom_map()`.
numbers = [1, 2, 3, 4, 5]

print(list(map(str, numbers)))


def custom_map(function, iterable):
from functools import reduce

return reduce(
lambda items, value: items + [function(value)],
iterable,
[],
)


print(list(custom_map(str, numbers)))


# Compare `filter()` to `custom_filter()`.
numbers = list(range(10))


def is_even(x):
return x % 2 == 0


print(list(filter(is_even, numbers)))


def custom_filter(function, iterable):
from functools import reduce

return reduce(
lambda items, value: items + [value] if function(value) else items,
iterable,
[],
)


print(list(custom_filter(is_even, numbers)))
30 changes: 30 additions & 0 deletions functional-programming-python/lambda_expressions.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
"""
Examples of writing lambda expressions.
"""


# Reverse a string.
def reverse(s):
return s[::-1]


reverse("I am a string")


reverse = lambda s: s[::-1] # noqa E731
print(reverse("I am a string"))

print((lambda s: s[::-1])("I am a string"))


# Calculate the average of three numbers.
print((lambda x1, x2, x3: (x1 + x2 + x3) / 3)(9, 6, 6))
print((lambda x1, x2, x3: (x1 + x2 + x3) / 3)(1.4, 1.1, 0.5))

# Return a fixed value.
forty_two_producer = lambda: 42 # noqa E731
print(forty_two_producer())

# Use a conditional expression.
print((lambda x: "even" if x % 2 == 0 else "odd")(2))
print((lambda x: "even" if x % 2 == 0 else "odd")(3))
22 changes: 22 additions & 0 deletions functional-programming-python/map_multiple.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
Example of using multiple iterables as arguments to `map()`.
"""


def add_three(a, b, c):
return a + b + c


print(list(map(add_three, [1, 2, 3], [10, 20, 30], [100, 200, 300])))

# Using a lambda expression.
print(
list(
map(
(lambda a, b, c: a + b + c),
[1, 2, 3],
[10, 20, 30],
[100, 200, 300],
)
)
)
37 changes: 37 additions & 0 deletions functional-programming-python/map_single.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
"""
Examples of using `map()` with a single iterable.
"""


def reverse(s):
return s[::-1]


print(reverse("I am a string"))

animals = ["cat", "dog", "hedgehog", "gecko"]

# Use `map()` to create an iterator.
iterator = map(reverse, animals)
print(iterator)

# Consume the iterator with a for loop.
iterator = map(reverse, animals)
for i in iterator:
print(i)

# Consume the iterator with a call to `list()`.
iterator = map(reverse, animals)
print(list(iterator))


# Use a lambda expression.
iterator = map(lambda s: s[::-1], animals)
print(list(iterator))


# All the code in a single line.
print(list(map(lambda s: s[::-1], ["cat", "dog", "hedgehog", "gecko"])))

# Convert integers to strings before concatenating them.
print("+".join(map(str, [1, 2, 3, 4, 5])))
20 changes: 20 additions & 0 deletions functional-programming-python/reduce_with_initializer.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
"""
Examples of using `reduce()` with an initializer value.
"""

from functools import reduce


def add_two_values(x, y):
return x + y


# Initialize with the value `100`.
# (100 + 1 + 2 + 3 + 4 + 5)
print(reduce(add_two_values, [1, 2, 3, 4, 5], 100))

# Use a lambda expression.
print(reduce(lambda x, y: x + y, [1, 2, 3, 4, 5], 100))

# Use `sum()` and add a value instead.
print(100 + sum([1, 2, 3, 4, 5]))
58 changes: 58 additions & 0 deletions functional-programming-python/reduce_with_two.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
"""
Examples of using `reduce()` with two arguments.
"""

from functools import reduce


# Sum elements in an iterable.
def add_two_values(x, y):
return x + y


print(reduce(add_two_values, [1, 2, 3, 4, 5]))
print(sum([1, 2, 3, 4, 5]))


# Concatenate strings.
print(reduce(add_two_values, ["cat", "dog", "hedgehog", "gecko"]))
print("".join(["cat", "dog", "hedgehog", "gecko"]))


# Calculate the factorial with `reduce()`.
def multiply(x, y):
return x * y


def factorial_with_reduce(n):
from functools import reduce

return reduce(multiply, range(1, n + 1))


print(factorial_with_reduce(4)) # 1 * 2 * 3 * 4
print(factorial_with_reduce(6)) # 1 * 2 * 3 * 4 * 5 * 6


# Calculate the factorial with `math.factorial()`.
from math import factorial # noqa E402

print(factorial(4))
print(factorial(6))


# Identify the maximum value.
print(max([23, 49, 6, 32]))


def greater(x, y):
return x if x > y else y


print(reduce(greater, [23, 49, 6, 32]))


# Use lambda expressions to complete the tasks.
print(reduce(lambda x, y: x + y, [1, 2, 3, 4, 5]))
print(reduce(lambda x, y: x + y, ["foo", "bar", "baz", "quz"]))
print(reduce((lambda x, y: x if x > y else y), [23, 49, 6, 32]))
Loading