Presentation is loading. Please wait.

Presentation is loading. Please wait.

Functions Functions being objects means functions can be passed into other functions: sort (list, key=str.upper)

Similar presentations


Presentation on theme: "Functions Functions being objects means functions can be passed into other functions: sort (list, key=str.upper)"— Presentation transcript:

1 Functions Functions being objects means functions can be passed into other functions: sort (list, key=str.upper)

2 Builtins sorted(iterable, key=None, reverse=False) As we've seen, returns a copy of iterable, sorted. The optional arguments must be kwargs. "reverse" will sort in reverse if set to True. "key" should be a function within the data of one argument that generates a value for comparing during sorting. e.g. key = str.lower Will sort as if all strings are lowercase (otherwise all capitals are more important than all lowercase) . Basically, it calls the method and passes in each item, and sorts the returned values.

3 Builtins: lists map(function, iterable, …)
Applies function to iterable as an iterator: for value in map(ord, ["A","B","C"]): # ord returns ACSII numbers print(value)

4 Lambdas "headless" or "anonymous" functions: i.e. short functions without names. Can only contain expressions, not statements (e.g. variable assignments). for square in map(lambda x: x**2, [1,2,3,4,5]): print(str(square)) # 1, 4, 9, 16, 25 for added in map(lambda x,y: x+y, [1,2,3,4,5],[1,2,3,4,5]): print(str(added)) # 2, 4, 6, 8, 10 b = "fire walk with me".split(" ") for a in map(lambda x: x[::-1], b): print(a) # erif klaw htiw em Beware adding lambdas to sequences as they get added as functions, not the result of functions:

5 Reduce functools.reduce(function, iterable)
Applies function cumulatively, so: def power(a, b): return a ** b import functools c = [2,3,4,5] d = functools.reduce(power, c) # (((2**3)**4)**5) print(d) or reduce(lambda x, y: x+y, [1, 2, 3, 4, 5]) # ((((1+2)+3)+4)+5) x is accumulator, y is each subsequent value. functools.update_wrapper: wraps around functions, passing in and returning parameters from another function that wraps around it.

6 Filter filter(function, sequence) filters out anything in sequence which function says is false. See also various iterators that apply functions to sequences in:

7 Decorators Enhance functions by wrapping them in code.
e.g. Least Recently Used cache: @lru_cache(maxsize=32) def get_lat_long(location): return lookup(location) for c in "Leeds", "Manchester", "Sheffield", "Liverpool", "Leeds": print(get_lat_long(c)) Saves the last 32 runs of this function for quick repeat; "memoizing" For more, see:

8 List comprehensions Essentially slightly easier and more flexible lambdas for setting up lists: listA = [1,2,3,4] listB = [2*x for x in listA] print(listB) # [2, 4, 6, 8] listB = [2* x for x in range(1:5)] print(listB) # [2, 4, 6, 8] listB = [2*x for x in listA if x % 2 == 0] # Even numbers only print(listB) # [4, 8] Can also be used to apply a function to everything in a list. listB = [ord(x) for x in listA]

9 Combinatorics List comprehensions can be used to generate combinations of values: listA = [(x, y) for x in [1,2,3] for y in ["a","b","c"]] print(listA) [(1, 'a'), (1, 'b'), (1, 'c'), (2, 'a'), (2, 'b'), (2, 'c'), (3, 'a'), (3, 'b'), (3, 'c')] Essentially like developing tuples from nested for-each loops. For a tuple, you have to use a parenthesis here or you get a syntax error.

10 Generator expressions
Generator expressions: exactly like list comprehensions, but generate an item at a time, so more memory efficient: listA = [1,2,3,4] notListB = (2* x for x in range(1,5)) for i in notListB : print(i) # Works print(notListB) # Doesn't print contents as don't exist.

11 Scope The scope of variables created inside lambdas, list comprehensions, and generator expresions is the function outlined, which some people like, as it doesn't create free variables slooping around the code afterwards. You can still use variables created earlier within these constructions, though obviously that would be bad practice if one wanted to isolate this code from side effects. From the docs: “A scope is a textual region of a Python program where a namespace is directly accessible. “Directly accessible” here means that an unqualified reference to a name attempts to find the name in the namespace.” “For example, assume we want to create a list of squares, like: >>>>>> squares = [] >>> for x in range(10): ... squares.append(x**2) ... >>> squares [0, 1, 4, 9, 16, 25, 36, 49, 64, 81] Note that this creates (or overwrites) a variable named x that still exists after the loop completes. We can calculate the list of squares without any side effects using: squares = list(map(lambda x: x**2, range(10))) or, equivalently: squares = [x**2 for x in range(10)] which is more concise and readable. A list comprehension consists of brackets containing an expression followed by a for clause, then zero or more for or if clauses. [(x, y) for x in [1,2,3] for y in [3,1,4] if x != y] If the expression is a tuple (e.g. the (x, y) in the previous example), it must be parenthesized."

12 Generator functions def count(): a = 0 while True:
yield a # Returns control and waits next call. a = a + 1 b = count() print (next(b)) Where the condition is just set to True, they will generate infinite sequences. Must be attached to a variable so they are called from the same instance each time and the method level variables aren't wiped; this doesn't work: print (next(count())) Can also be used: for i in count(): print(i) To pass values into these, see:


Download ppt "Functions Functions being objects means functions can be passed into other functions: sort (list, key=str.upper)"

Similar presentations


Ads by Google