ch11
This commit is contained in:
parent
0c8daddd31
commit
3cebc2fe91
28
ch11/assertions.py
Normal file
28
ch11/assertions.py
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
# assertions.py
|
||||||
|
mylist = [1, 2, 3] # pretend this comes from an external source
|
||||||
|
|
||||||
|
assert 4 == len(mylist) # this will break
|
||||||
|
|
||||||
|
for position in range(4):
|
||||||
|
print(mylist[position])
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python assertions.py
|
||||||
|
Traceback (most recent call last):
|
||||||
|
File "assertions.py", line 4, in <module>
|
||||||
|
assert 4 == len(mylist) # this will break
|
||||||
|
AssertionError
|
||||||
|
"""
|
||||||
|
|
||||||
|
# asserts with message
|
||||||
|
assert 4 == len(mylist), f"Mylist has {len(mylist)} elements"
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python assertions.py
|
||||||
|
Traceback (most recent call last):
|
||||||
|
File "assertions.py", line 19, in <module>
|
||||||
|
assert 4 == len(mylist), f"Mylist has {len(mylist)} elements"
|
||||||
|
AssertionError: Mylist has 3 elements
|
||||||
|
"""
|
||||||
20
ch11/custom.py
Normal file
20
ch11/custom.py
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
# custom.py
|
||||||
|
def debug(*msg, print_separator=True):
|
||||||
|
print(*msg)
|
||||||
|
if print_separator:
|
||||||
|
print('-' * 40)
|
||||||
|
|
||||||
|
|
||||||
|
debug('Data is ...')
|
||||||
|
debug('Different', 'Strings', 'Are not a problem')
|
||||||
|
debug('After while loop', print_separator=False)
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python custom.py
|
||||||
|
Data is ...
|
||||||
|
----------------------------------------
|
||||||
|
Different Strings Are not a problem
|
||||||
|
----------------------------------------
|
||||||
|
After while loop
|
||||||
|
"""
|
||||||
32
ch11/custom_timestamp.py
Normal file
32
ch11/custom_timestamp.py
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
# custom_timestamp.py
|
||||||
|
from time import sleep
|
||||||
|
|
||||||
|
|
||||||
|
def debug(*msg, timestamp=[None]):
|
||||||
|
print(*msg)
|
||||||
|
from time import time # local import
|
||||||
|
if timestamp[0] is None:
|
||||||
|
timestamp[0] = time() #1
|
||||||
|
else:
|
||||||
|
now = time()
|
||||||
|
print(
|
||||||
|
' Time elapsed: {:.3f}s'.format(now - timestamp[0])
|
||||||
|
)
|
||||||
|
timestamp[0] = now #2
|
||||||
|
|
||||||
|
|
||||||
|
debug('Entering nasty piece of code...')
|
||||||
|
sleep(.3)
|
||||||
|
debug('First step done.')
|
||||||
|
sleep(.5)
|
||||||
|
debug('Second step done.')
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python custom_timestamp.py
|
||||||
|
Entering nasty piece of code...
|
||||||
|
First step done.
|
||||||
|
Time elapsed: 0.300s
|
||||||
|
Second step done.
|
||||||
|
Time elapsed: 0.500s
|
||||||
|
"""
|
||||||
21
ch11/log.py
Normal file
21
ch11/log.py
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
# log.py
|
||||||
|
import logging
|
||||||
|
|
||||||
|
logging.basicConfig(
|
||||||
|
filename='ch11.log',
|
||||||
|
level=logging.DEBUG,
|
||||||
|
format='[%(asctime)s] %(levelname)s: %(message)s',
|
||||||
|
datefmt='%m/%d/%Y %I:%M:%S %p')
|
||||||
|
|
||||||
|
mylist = [1, 2, 3]
|
||||||
|
logging.info('Starting to process `mylist`...')
|
||||||
|
|
||||||
|
for position in range(4):
|
||||||
|
try:
|
||||||
|
logging.debug(
|
||||||
|
'Value at position %s is %s', position, mylist[position]
|
||||||
|
)
|
||||||
|
except IndexError:
|
||||||
|
logging.exception('Faulty position: %s', position)
|
||||||
|
|
||||||
|
logging.info('Done processing `mylist`.')
|
||||||
23
ch11/pdebugger.py
Normal file
23
ch11/pdebugger.py
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
# pdebugger.py
|
||||||
|
# d comes from a JSON payload we don't control
|
||||||
|
d = {'first': 'v1', 'second': 'v2', 'fourth': 'v4'}
|
||||||
|
# keys also comes from a JSON payload we don't control
|
||||||
|
keys = ('first', 'second', 'third', 'fourth')
|
||||||
|
|
||||||
|
def do_something_with_value(value):
|
||||||
|
print(value)
|
||||||
|
|
||||||
|
for key in keys:
|
||||||
|
do_something_with_value(d[key])
|
||||||
|
|
||||||
|
print('Validation done.')
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python pdebugger.py
|
||||||
|
v1
|
||||||
|
v2
|
||||||
|
Traceback (most recent call last):
|
||||||
|
File "pdebugger.py", line 11, in <module>
|
||||||
|
do_something_with_value(d[key])
|
||||||
|
KeyError: 'third'
|
||||||
|
"""
|
||||||
45
ch11/pdebugger_pdb.py
Normal file
45
ch11/pdebugger_pdb.py
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
# pdebugger_pdb.py
|
||||||
|
# d comes from a JSON payload we don't control
|
||||||
|
d = {'first': 'v1', 'second': 'v2', 'fourth': 'v4'}
|
||||||
|
# keys also comes from a JSON payload we don't control
|
||||||
|
keys = ('first', 'second', 'third', 'fourth')
|
||||||
|
|
||||||
|
def do_something_with_value(value):
|
||||||
|
print(value)
|
||||||
|
|
||||||
|
|
||||||
|
import pdb
|
||||||
|
pdb.set_trace()
|
||||||
|
|
||||||
|
# or:
|
||||||
|
# breakpoint()
|
||||||
|
|
||||||
|
|
||||||
|
for key in keys:
|
||||||
|
do_something_with_value(d[key])
|
||||||
|
|
||||||
|
print('Validation done.')
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python pdebugger_pdb.py
|
||||||
|
[0] > pdebugger_pdb.py(17)<module>()
|
||||||
|
-> for key in keys:
|
||||||
|
(Pdb++) l
|
||||||
|
17
|
||||||
|
18 -> for key in keys: # breakpoint comes in
|
||||||
|
19 do_something_with_value(d[key])
|
||||||
|
20
|
||||||
|
|
||||||
|
(Pdb++) keys # inspecting the keys tuple
|
||||||
|
('first', 'second', 'third', 'fourth')
|
||||||
|
(Pdb++) d.keys() # inspecting keys of `d`
|
||||||
|
dict_keys(['first', 'second', 'fourth'])
|
||||||
|
(Pdb++) d['third'] = 'placeholder' # add missing item
|
||||||
|
(Pdb++) c # continue
|
||||||
|
v1
|
||||||
|
v2
|
||||||
|
placeholder
|
||||||
|
v4
|
||||||
|
Validation done.
|
||||||
|
"""
|
||||||
37
ch11/profiling/triples.py
Normal file
37
ch11/profiling/triples.py
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
|
||||||
|
def calc_triples(mx):
|
||||||
|
triples = []
|
||||||
|
for a in range(1, mx + 1):
|
||||||
|
for b in range(a, mx + 1):
|
||||||
|
hypotenuse = calc_hypotenuse(a, b)
|
||||||
|
if is_int(hypotenuse):
|
||||||
|
triples.append((a, b, int(hypotenuse)))
|
||||||
|
return triples
|
||||||
|
|
||||||
|
|
||||||
|
def calc_hypotenuse(a, b):
|
||||||
|
return (a**2 + b**2) ** .5
|
||||||
|
|
||||||
|
|
||||||
|
def is_int(n): # n is expected to be a float
|
||||||
|
return n.is_integer()
|
||||||
|
|
||||||
|
|
||||||
|
triples = calc_triples(1000)
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python -m cProfile profiling/triples.py
|
||||||
|
1502538 function calls in 0.489 seconds
|
||||||
|
|
||||||
|
Ordered by: standard name
|
||||||
|
|
||||||
|
ncalls tottime percall cumtime percall filename:lineno(function)
|
||||||
|
500500 0.282 0.000 0.282 0.000 triples.py:13(calc_hypotenuse)
|
||||||
|
500500 0.065 0.000 0.086 0.000 triples.py:17(is_int)
|
||||||
|
1 0.000 0.000 0.489 0.489 triples.py:3(<module>)
|
||||||
|
1 0.121 0.121 0.489 0.489 triples.py:3(calc_triples)
|
||||||
|
1 0.000 0.000 0.489 0.489 {built-in method builtins.exec}
|
||||||
|
1034 0.000 0.000 0.000 0.000 {method 'append' of 'list' objects}
|
||||||
|
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}
|
||||||
|
500500 0.021 0.000 0.021 0.000 {method 'is_integer' of 'float' objects}
|
||||||
|
"""
|
||||||
37
ch11/profiling/triples_v2.py
Normal file
37
ch11/profiling/triples_v2.py
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
|
||||||
|
def calc_triples(mx):
|
||||||
|
triples = []
|
||||||
|
for a in range(1, mx + 1):
|
||||||
|
for b in range(a, mx + 1):
|
||||||
|
hypotenuse = calc_hypotenuse(a, b)
|
||||||
|
if is_int(hypotenuse):
|
||||||
|
triples.append((a, b, int(hypotenuse)))
|
||||||
|
return triples
|
||||||
|
|
||||||
|
|
||||||
|
def calc_hypotenuse(a, b):
|
||||||
|
return (a*a + b*b) ** .5
|
||||||
|
|
||||||
|
|
||||||
|
def is_int(n): # n is expected to be a float
|
||||||
|
return n.is_integer()
|
||||||
|
|
||||||
|
|
||||||
|
triples = calc_triples(1000)
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python -m cProfile profiling/triples_v2.py
|
||||||
|
1502538 function calls in 0.288 seconds
|
||||||
|
|
||||||
|
Ordered by: standard name
|
||||||
|
|
||||||
|
ncalls tottime percall cumtime percall filename:lineno(function)
|
||||||
|
500500 0.084 0.000 0.084 0.000 triples_v2.py:13(calc_hypotenuse)
|
||||||
|
500500 0.064 0.000 0.084 0.000 triples_v2.py:17(is_int)
|
||||||
|
1 0.000 0.000 0.288 0.288 triples_v2.py:3(<module>)
|
||||||
|
1 0.120 0.120 0.288 0.288 triples_v2.py:3(calc_triples)
|
||||||
|
1 0.000 0.000 0.288 0.288 {built-in method builtins.exec}
|
||||||
|
1034 0.000 0.000 0.000 0.000 {method 'append' of 'list' objects}
|
||||||
|
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}
|
||||||
|
500500 0.020 0.000 0.020 0.000 {method 'is_integer' of 'float' objects}
|
||||||
|
"""
|
||||||
36
ch11/profiling/triples_v3.py
Normal file
36
ch11/profiling/triples_v3.py
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
|
||||||
|
def calc_triples(mx):
|
||||||
|
triples = []
|
||||||
|
for a in range(1, mx + 1):
|
||||||
|
for b in range(a, mx + 1):
|
||||||
|
hypotenuse = calc_hypotenuse(a, b)
|
||||||
|
if is_int(hypotenuse):
|
||||||
|
triples.append((a, b, int(hypotenuse)))
|
||||||
|
return triples
|
||||||
|
|
||||||
|
|
||||||
|
def calc_hypotenuse(a, b):
|
||||||
|
return (a*a + b*b) ** .5
|
||||||
|
|
||||||
|
|
||||||
|
def is_int(n):
|
||||||
|
return n == int(n)
|
||||||
|
|
||||||
|
|
||||||
|
triples = calc_triples(1000)
|
||||||
|
|
||||||
|
"""
|
||||||
|
$ python -m cProfile profiling/triples_v3.py
|
||||||
|
1002038 function calls in 0.269 seconds
|
||||||
|
|
||||||
|
Ordered by: standard name
|
||||||
|
|
||||||
|
ncalls tottime percall cumtime percall filename:lineno(function)
|
||||||
|
500500 0.084 0.000 0.084 0.000 triples_v3.py:13(calc_hypotenuse)
|
||||||
|
500500 0.068 0.000 0.068 0.000 triples_v3.py:17(is_int)
|
||||||
|
1 0.000 0.000 0.269 0.269 triples_v3.py:3(<module>)
|
||||||
|
1 0.116 0.116 0.269 0.269 triples_v3.py:3(calc_triples)
|
||||||
|
1 0.000 0.000 0.269 0.269 {built-in method builtins.exec}
|
||||||
|
1034 0.000 0.000 0.000 0.000 {method 'append' of 'list' objects}
|
||||||
|
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}
|
||||||
|
"""
|
||||||
1
ch11/requirements.in
Normal file
1
ch11/requirements.in
Normal file
@ -0,0 +1 @@
|
|||||||
|
pdbpp
|
||||||
16
ch11/requirements.txt
Normal file
16
ch11/requirements.txt
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
#
|
||||||
|
# This file is autogenerated by pip-compile with python 3.9
|
||||||
|
# To update, run:
|
||||||
|
#
|
||||||
|
# pip-compile requirements.in
|
||||||
|
#
|
||||||
|
fancycompleter==0.9.1
|
||||||
|
# via pdbpp
|
||||||
|
pdbpp==0.10.3
|
||||||
|
# via -r requirements.in
|
||||||
|
pygments==2.9.0
|
||||||
|
# via pdbpp
|
||||||
|
pyrepl==0.9.0
|
||||||
|
# via fancycompleter
|
||||||
|
wmctrl==0.4
|
||||||
|
# via pdbpp
|
||||||
Loading…
x
Reference in New Issue
Block a user