updated from Atlas

This commit is contained in:
Luciano Ramalho
2015-04-01 22:48:56 -03:00
parent aab93699a4
commit 573e1a94c4
109 changed files with 5 additions and 6 deletions

View File

@@ -0,0 +1,20 @@
"""
>>> avg = make_averager()
>>> avg(10)
Traceback (most recent call last):
...
UnboundLocalError: local variable 'num_items' referenced before assignment
"""
def make_averager():
num_items = 0
total = 0
def averager(new_value):
num_items += 1
total += new_value
return total / num_items
return averager

View File

@@ -0,0 +1,45 @@
"""
>>> avg = make_averager()
>>> other_avg = make_averager()
>>> avg(10)
10.0
>>> avg(11)
10.5
>>> avg(12)
11.0
>>> avg.__code__.co_varnames
('new_value',)
>>> avg.__code__.co_freevars
('num_items', 'total')
>>> avg.__closure__ # doctest: +ELLIPSIS
(<cell at 0x...: int object at 0x...>, <cell at 0x...: int object at 0x...>)
>>> avg.__closure__[0].cell_contents
3
>>> avg.__closure__[1].cell_contents
33
>>> other_avg(5)
5.0
>>> other_avg(10)
7.5
>>> other_avg(15)
10.0
"""
DEMO = """
>>> avg.__closure__
(<cell at 0x10fd24f78: int object at 0x10f6d3db0>,
<cell at 0x10fd24d38: int object at 0x10f6d4170>)
"""
def make_averager():
num_items = 0
total = 0
def averager(new_value):
nonlocal num_items, total
num_items += 1
total += new_value
return total / num_items
return averager

View File

@@ -0,0 +1,39 @@
"""
>>> avg = make_averager()
>>> avg(10)
10.0
>>> avg(11)
10.5
>>> avg(12)
11.0
>>> avg.__code__.co_varnames
('new_value',)
>>> avg.__code__.co_freevars
('ns',)
>>> avg.__closure__ # doctest: +ELLIPSIS
(<cell at 0x...: Namespace object at 0x...>,)
>>> avg.__closure__[0].cell_contents.__dict__
{'total': 33, 'num_items': 3}
"""
DEMO = """
>>> avg.__closure__
(<cell at 0x108df5980: Namespace object at 0x108e06790>,)
"""
class Namespace(object):
pass
def make_averager():
ns = Namespace()
ns.num_items = 0
ns.total = 0
def averager(new_value):
ns.num_items += 1
ns.total += new_value
return float(ns.total) / ns.num_items
return averager

View File

@@ -0,0 +1,34 @@
"""
>>> import functools
>>> avg = functools.partial(averager, series=[])
>>> avg(10)
10.0
>>> avg(11)
10.5
>>> avg(12)
11.0
>>> avg.args
()
>>> avg.keywords
{'series': [10, 11, 12]}
>>> avg.func # doctest: +ELLIPSIS
<function averager at 0x...>
>>> avg.func.__code__.co_varnames
('new_value', 'series', 'total')
"""
DEMO = """
>>> avg.func
<function averager at 0x1010c5560>
>>> avg.func.__code__.co_varnames
('new_value',)
>>> avg.__code__.co_freevars
('num_items', 'total')
>>> avg.__closure__
"""
def averager(new_value, series):
series.append(new_value)
total = sum(series)
return float(total)/len(series)

View File

@@ -0,0 +1,28 @@
"""
>>> avg = make_averager()
>>> avg(10)
10.0
>>> avg(11)
10.5
>>> avg(12)
11.0
>>> avg.__code__.co_varnames
('new_value', 'total')
>>> avg.__code__.co_freevars
('series',)
>>> avg.__closure__ # doctest: +ELLIPSIS
(<cell at 0x...: list object at 0x...>,)
>>> avg.__closure__[0].cell_contents
[10, 11, 12]
"""
def make_averager():
series = []
def averager(new_value):
series.append(new_value)
total = sum(series)
return float(total)/len(series)
return averager

View File

@@ -0,0 +1,15 @@
# clockdeco.py
import time
def clock(func):
def clocked(*args):
t0 = time.time()
result = func(*args)
elapsed = time.time() - t0
name = func.__name__
arg_str = ', '.join(repr(arg) for arg in args)
print('[%0.8fs] %s(%s) -> %r' % (elapsed, name, arg_str, result))
return result
return clocked

View File

@@ -0,0 +1,23 @@
# clockdeco2.py
import time
import functools
def clock(func):
@functools.wraps(func)
def clocked(*args, **kwargs):
t0 = time.time()
result = func(*args, **kwargs)
elapsed = time.time() - t0
name = func.__name__
arg_lst = []
if args:
arg_lst.append(', '.join(repr(arg) for arg in args))
if kwargs:
pairs = ['%s=%r' % (k, w) for k, w in sorted(kwargs.items())]
arg_lst.append(', '.join(pairs))
arg_str = ', '.join(arg_lst)
print('[%0.8fs] %s(%s) -> %r ' % (elapsed, name, arg_str, result))
return result
return clocked

View File

@@ -0,0 +1,31 @@
# clockdec2o_demo.py
"""
>>> pythagoras(3, 4) # doctest: +ELLIPSIS
[0.0...s] pythagoras(3, 4) -> 5.0
5.0
>>> pythagoras(9, h=15) # doctest: +ELLIPSIS
[0.0...s] pythagoras(9, h=15) -> 12.0
12.0
"""
import time
import math
from clockdeco2 import clock
@clock
def pythagoras(a, b=None, h=None):
if b is None and h is None:
raise TypeError('must provide second leg (b) or hypotenuse (h)')
if h is None:
return math.sqrt(a*a + b*b)
else:
return math.sqrt(h*h - a*a)
if __name__=='__main__':
print('*' * 40, 'Calling pythagoras(3, 4)')
pythagoras(3, 4)
print('*' * 40, 'Calling pythagoras(9, h=15)')
pythagoras(9, h=15)

View File

@@ -0,0 +1,95 @@
"""
>>> f_empty()
[0.0...s] f_empty() -> None
>>> f_args('spam', 3)
[0.0...s] f_args('spam', 3) -> 'spamspamspam'
'spamspamspam'
>>> snooze(1234)
[1...s] snooze(1234) -> None
>>> average(1, 2, 3)
[0.0...s] average(1, 2, 3) -> 2.0
2.0
>>> average(*range(10**3))
[0.0...s] average(0, 1, ..., 999) -> 499.5
499.5
>>> factorial(10)
[0.000...s] factorial(1) -> 1
[0.000...s] factorial(2) -> 2
[0.000...s] factorial(3) -> 6
[0.000...s] factorial(4) -> 24
[0.000...s] factorial(5) -> 120
[0.000...s] factorial(6) -> 720
[0.000...s] factorial(7) -> 5040
[0.000...s] factorial(8) -> 40320
[0.000...s] factorial(9) -> 362880
[0.000...s] factorial(10) -> 3628800
3628800
>>> fibonacci(1)
[0.000...s] fibonacci(1) -> 1
1
>>> fibonacci(5)
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(3) -> 2
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(3) -> 2
[0.000...s] fibonacci(4) -> 3
[0.000...s] fibonacci(5) -> 5
5
>>> f_kwargs(3, 5, d='spam', c='eggs')
[0.0...s] f_kwargs(3, 5, c='eggs', d='spam') -> 15
15
>>> f_args.__name__
'f_args'
>>> f_kwargs.__name__
'f_kwargs'
"""
import time
from clockdeco2 import clock
@clock
def f_empty():
pass
@clock
def f_args(a, b):
return a*b
@clock
def snooze(milis):
time.sleep(milis/1000)
@clock
def average(*args):
return sum(args) / len(args)
@clock
def factorial(n):
return 1 if n < 2 else n*factorial(n-1)
@clock
def fibonacci(n):
if n < 2:
return n
return fibonacci(n-2) + fibonacci(n-1)
@clock
def f_kwargs(a, b, c=1, d='eggs'):
from time import sleep
sleep(0.001)
return a*b
import doctest
doctest.testmod(optionflags=doctest.ELLIPSIS | doctest.NORMALIZE_WHITESPACE)

View File

@@ -0,0 +1,22 @@
from clockdeco import clock
import time
@clock
def snooze(milis):
time.sleep(milis/1000)
@clock
def factorial(n):
return 1 if n < 2 else n*factorial(n-1)
@clock
def fibonacci(n):
if n < 2:
return n
return fibonacci(n-2) + fibonacci(n-1)
snooze(123)
print(factorial(6))
print(fibonacci(4))

View File

@@ -0,0 +1,20 @@
import functools
from clockdeco import clock
@functools.lru_cache()
@clock
def factorial(n):
return 1 if n < 2 else n*factorial(n-1)
@functools.lru_cache()
@clock
def fibonacci(n):
if n < 2:
return n
return fibonacci(n-2) + fibonacci(n-1)
print(factorial(6))
print(fibonacci(6))

View File

@@ -0,0 +1,82 @@
"""
>>> f_empty()
[0.0...s] f_empty() -> None
>>> f_args('spam', 3)
[0.0...s] f_args('spam', 3) -> 'spamspamspam'
'spamspamspam'
>>> snooze(1234)
[1...s] snooze(1234) -> None
>>> average(1, 2, 3)
[0.0...s] average(1, 2, 3) -> 2.0
2.0
>>> average(*range(10**3))
[0.0...s] average(0, 1, ..., 999) -> 499.5
499.5
>>> factorial(10)
[0.000...s] factorial(1) -> 1
[0.000...s] factorial(2) -> 2
[0.000...s] factorial(3) -> 6
[0.000...s] factorial(4) -> 24
[0.000...s] factorial(5) -> 120
[0.000...s] factorial(6) -> 720
[0.000...s] factorial(7) -> 5040
[0.000...s] factorial(8) -> 40320
[0.000...s] factorial(9) -> 362880
[0.000...s] factorial(10) -> 3628800
3628800
>>> fibonacci(1)
[0.000...s] fibonacci(1) -> 1
1
>>> fibonacci(5)
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(3) -> 2
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(0) -> 0
[0.000...s] fibonacci(1) -> 1
[0.000...s] fibonacci(2) -> 1
[0.000...s] fibonacci(3) -> 2
[0.000...s] fibonacci(4) -> 3
[0.000...s] fibonacci(5) -> 5
5
>>> f_args.__name__
'clocked'
"""
import time
from clockdeco import clock
@clock
def f_empty():
pass
@clock
def f_args(a, b):
return a*b
@clock
def snooze(milis):
time.sleep(milis/1000)
@clock
def average(*args):
return sum(args) / len(args)
@clock
def factorial(n):
return 1 if n < 2 else n*factorial(n-1)
@clock
def fibonacci(n):
if n < 2:
return n
return fibonacci(n-2) + fibonacci(n-1)
import doctest
doctest.testmod(optionflags=doctest.ELLIPSIS | doctest.NORMALIZE_WHITESPACE)

View File

@@ -0,0 +1,50 @@
# currency.py
"""
>>> convert(1, 'BRL', 'USD')
0.4591
>>> convert(1, 'USD', 'BRL')
2.1784
>>> convert(1, 'EUR', 'USD')
1.3482
>>> convert(1, 'USD', 'EUR')
0.7417
>>> convert(1, 'EUR', 'BRL')
2.9369
>>> convert(1, 'BRL', 'EUR')
0.3405
>>> from functools import partial
>>> eur = partial(convert, cur_to='EUR')
>>> eur(1, 'USD')
0.7417
>>> eur(1, 'BRL')
0.3405
>>> eur2brl = partial(convert, cur_from='EUR', cur_to='BRL')
>>> eur2brl(100)
293.6864
>>> type(eur2brl)
<class 'functools.partial'>
"""
DEMO = """
>>> eur2brl.func
<function convert at 0x1010c5560>
>>> eur2brl.args, eur2brl.keywords
((), {'cur_from': 'EUR', 'cur_to': 'BRL'})
"""
rates = {'BRL': 2.17836,
'CAD': 1.03615,
'CNY': 6.10562,
'EUR': 0.74173,
'GBP': 0.62814,
'INR': 61.8685,
'JPY': 98.6002,
'USD': 1.0}
reference = rates['USD']
def convert(amount, cur_from, cur_to):
ref_amount = reference / rates[cur_from] * amount
return round(ref_amount * rates[cur_to], 4)

View File

@@ -0,0 +1,60 @@
# source: http://oeis.org/A000045
fibo_seq = [0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610,
987, 1597, 2584, 4181, 6765, 10946, 17711, 28657, 46368, 75025,
121393, 196418, 317811, 514229, 832040, 1346269, 2178309,
3524578, 5702887, 9227465, 14930352, 24157817, 39088169]
from functools import lru_cache
def fibonacci(n):
if n < 2:
return n
return fibonacci(n-2) + fibonacci(n-1)
@lru_cache()
def fibonacci2(n):
if n < 2:
return n
return fibonacci2(n-2) + fibonacci2(n-1)
def memoize(func):
'''simplest memoizing decorator'''
cache = {}
def memoized(*args):
if args not in cache:
cache[args] = func(*args)
return cache[args]
return memoized
def test():
for i, expected in enumerate(fibo_seq[:31]):
print(i, expected)
assert fibonacci(i) == expected
def chronograph():
global fibonacci
from time import time
t0 = time()
n = 32
res = fibonacci(n)
#res = [fibonacci(n) for n in range(30)]
t1 = time()
print(n, res, format(t1-t0, '0.6f'))
t0 = time()
res = fibonacci2(n)
#res = [fibonacci2(n) for n in range(30)]
t1 = time()
print(n, res, format(t1-t0, '0.6f'))
t0 = time()
fibonacci = memoize(fibonacci)
res = fibonacci(n)
#res = [fibonacci2(n) for n in range(30)]
t1 = time()
print(n, res, format(t1-t0, '0.6f'))
if __name__=='__main__':
#test()
chronograph()

View File

@@ -0,0 +1,63 @@
"""
>>> f1(3)
>>> b = 8
>>> f1(3)
a = 3
b = 8
>>> f2(3)
Traceback (most recent call last):
...
UnboundLocalError: local variable 'b' referenced before assignment
>>> f3(3)
a = 3
b = 7
b = 6
>>> b = -5
>>> ff = f4()
>>> ff(3)
a = 3
b = 11
b = 6
>>> print('b =', b)
b = -5
"""
def f1(a):
print('a =', a)
print('b =', b)
def f2(a):
print('a =', a)
print('b =', b)
b = a * 10
print('b =', b)
def f3(a):
global b
print('a =', a)
print('b =', b)
b = a * 10
print('b =', b)
def f3b(a):
nonlocal b
print('a =', a)
print('b =', b)
b = a * 10
print('b =', b)
def f4():
b = 11
def f5(a):
nonlocal b
print('a =', a)
print('b =', b)
b = a * 2
print('b =', b)
return f5
import doctest
doctest.testmod(optionflags=doctest.ELLIPSIS | doctest.NORMALIZE_WHITESPACE)

View File

@@ -0,0 +1,27 @@
def d1(f):
def wrapped():
print('d1/wrapped')
return f()
return wrapped
def d2(f):
def wrapped():
print('d2/wrapped')
return f()
return wrapped
@d1
@d2
def f():
print('f')
f()
def g():
print('g')
g = d1(d2(g))
g()