- Default args example
def f(x, y=10): return (x,y)
print(f(5)) # (5, 10)
print(f(5,6)) # (5, 6)
- Do not use mutable default args
def f(x, L=[ ]):
L.append(x)
return L
print(f(1))
print(f(2)) # why is this [1, 2]?
- One workaround for mutable default args
def f(x, L=None):
if (L == None):
L = [ ]
L.append(x)
return L
print(f(1))
print(f(2)) # [2] (that's better)
- Functions as parameters
def derivative(f, x):
h = 10**-8
return (f(x+h) - f(x))/h
def f(x): return 4*x + 3
print(derivative(f, 2)) # about 4
def g(x): return 4*x**2 + 3
print(derivative(g, 2)) # about 16 (8*x at x==2)
- Lambda functions
print(derivative(lambda x:3*x**5 + 2, 2)) # about 240, 15*x**4 at x==2
myF = lambda x: 10*x + 42
print(myF(5)) # 92
print(derivative(myF, 5)) # about 10
- Functions inside functions
def f(L):
def squared(x): return x**2
return [squared(x) for x in L]
print(f(range(5)))
try:
print(squared(5))
except:
print("squared is not defined outside f")
- Closures + Non-local variables
def f(L):
myMap = dict()
def squared(x):
result = x**2
myMap[x] = result
return result
squaredList = [squared(x) for x in L]
return myMap
print(f(range(5)))
- Non-local variables fail on setting (use nonlocal)
def brokenF(L):
lastX = 0
def squared(x):
result = x**2
lastX = x
return result
squaredList = [squared(x) for x in L]
return lastX
print(brokenF(range(5)))
def fixedF(L):
lastX = 0
def squared(x):
nonlocal lastX
result = x**2
lastX = x
return result
squaredList = [squared(x) for x in L]
return lastX
print(fixedF(range(5)))