Hidden Treasures - Core Python
Hidden Treasures - Core Python
Introduction 1.1
01. Variables 1.2
02 Data Type 1.3
01 Data Type 1.3.1
02 Slices 1.3.2
03 Conditional Statements 1.4
04 Functions 1.5
05. OOPs 1.6
06. Operators 1.7
07. Generators and Iterators 1.8
08. IO 1.9
09. Exception 1.10
10 Modules 1.11
99. Easter Eggs 1.12
Hidden Treasures: Python
This ebook contains few lesser known Python gems which
developers can use to enhance their knowledge in Python and get
more productive.
Unicode identifier
Python 3 allows to have unicode identifier's, which allows non-
english speaking users to code.
िह दी = 10
print(िह दी)
10
Multi Assignation
Multiple Assignation
Multiple variables can be assigned different values in a single line
print(a, b, c)
0 1 2
a = b = c = "1001"
print(a, b, c)
print(id(a), id(b), id(c))
a = 10
b = "TEST"
a, b = b, a
print(a, b)
TEST 10
a = 10
b = "TEST"
print(sys.getsizeof(a))
print(sys.getsizeof(b))
print(sys.getsizeof([a, b]))
28
53
80
class X:
b = 10
x = X
print(sys.getsizeof(x))
x.a = list(range(10000))
print(sys.getsizeof(x))
print(sys.getsizeof(x.a))
print("Funny, x is smaller than x.a")
1056
1056
90112
Funny, x is smaller than x.a
Integer
Negative round
round is a function to round off the numbers and its normal usage
is as follows
num = round(283746.32321, 1)
print(num)
283746.3
115681
print(txt)
Using '\'
print(txt)
print("-^*" * 20)
-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*-^*
print("ash" in "ashwini")
True
False
print("ash" is 'ash')
True
True
True
True
False
Mayank Johri
using slices
1 2
[3, 4, 5, 'tst']
1 2
[3, 4, 5, 'tst']
first,*middle,last = (1,2,3,4,5,6,7,8)
print(first, last)
print(middle)
1 8
[2, 3, 4, 5, 6, 7]
first,*middle,last = [1,2,3,4,5,6,7,8]
print(first, last)
print(middle)
1 8
[2, 3, 4, 5, 6, 7]
List/tuple multiplication ;)
similar to String we can literally multiply string and tuples with
integer as shown below
lst = [1, 2, 3]
print(lst*3)
[1, 2, 3, 1, 2, 3, 1, 2, 3]
lst = (1, 2, 3)
print(lst*3)
(1, 2, 3, 1, 2, 3, 1, 2, 3)
[(0, 'Ashwini'),
(1, 'Banti'),
(2, 'Bhaiya'),
(3, 'Mayank'),
(4, 'Shashank'),
(5, 'Rahul')]
print(list(enumerate(lst, 10)))
print(list(reversed([1, 2, 3, 4, 53])))
[53, 4, 3, 2, 1]
Flattening of list
Method 1:
[1, 2, 3, 4, 5, 6, 7, 8, 9]
NOTE: this method will fail if any of the element is non list
item as shown in the below example
from itertools import chain
try:
flattened_list = list(chain(*l1))
print(flattened_list)
except Exception as e:
print(e)
Method 2:
[1, 2, 3, 4, 5, 6, 7, 8, 9]
NOTE: this method will fail if any of the element is non list
item as shown in the below example
try:
flattened_list = [y for x in l1 for y in x]
print(flattened_list)
except Exception as e:
print(e)
[1, 2, 3, 4, 5, 6, 7, 8, 9]
Method 3:
[1, 2, 3, 4, 5, 6, 7, 8, 9]
NOTE: this method will fail if any of the element is non list
item as shown in the below example
try:
sum(l1, [])
except Exception as e:
print(e)
Method 4:
flattened_list = []
for x in l:
for y in x:
flattened_list.append(y)
print(flattened_list)
[1, 2, 3, 4, 5, 6, 7, 8, 9]
NOTE: this method will fail if any of the element is non list
item as shown in the below example
try:
flattened_list = []
for x in l1:
for y in x:
flattened_list.append(y)
print(flattened_list)
except Exception as e:
print(e)
Method 5:
NOTE: this method will fail if any of the element is non list
item as shown in the below example
try:
flattened_list = reduce(lambda x, y: x + y, l1)
print(flattened_list)
except Exception as e:
print(e)
Method 6:
import operator
flattened_list = reduce(operator.add, l)
print(flattened_list)
[1, 2, 3, 4, 5, 6, 7, 8, 9]
NOTE: this method will fail if any of the element is non list
item as shown in the below example
import operator
try:
flattened_list = reduce(operator.add, l1)
print(flattened_list)
except Exception as e:
print(e)
Infinite Recursion
lst = [1, 2]
lst.append(lst)
print(lst)
[1, 2, [...]]
def test(lst):
for a in lst:
if isinstance(a, list):
print("A", a)
test(a)
print(a)
test(lst)
printing elements of list
Copy a list
Both the variables are still pointing to same list, thus change in one
will change another also.
dup.insert(0, 29)
print(brothers)
print(dup)
Deepcopy a list
ori = [1, 2, 3, 4, 5, 6]
dup = ori[:]
print(id(ori))
print(id(dup))
140307524228424
140307524230408
dup.insert(0, 29)
print(ori)
print(dup)
[1, 2, 3, 4, 5, 6]
[29, 1, 2, 3, 4, 5, 6]
ori = [1, 2, 3, 3, 4, 5, 5, 4, 5, 6, 4, 5, 6, ]
counter = Counter(ori)
print(counter.most_common())
[(5, 4), (4, 3), (3, 2), (6, 2), (1, 1), (2, 1)]
Dictionaries
Method 1:
capitals_states =
dict(zip(*list(zip(*states_capitals.items()))[::-1]))
print(capitals_states)
Method 2:
Method 3:
capitals_states = dict(zip(states_capitals.values(),
states_capitals.keys()))
print(capitals_states)
{'Bhopal': 'MP', 'Lucknow': 'UP', 'Jaipur': 'Rajasthan'}
or
capitals_states = dict(zip(states_capitals.values(),
states_capitals))
print(capitals_states)
or
Using arguments
list of tuples
lst = list(range(10))
d = {k : k * k for k in lst}
print(d)
calculator = {
'add': lambda x, y: x + y,
'subtract': lambda x, y: x - y,
'multiple': lambda x, y: x * y,
'div': lambda x, y: x % y
}
print(calculator['add'](15, 2))
print(calculator['subtract'](12, 11))
print(calculator['multiple'](15, 2))
print(calculator['div'](12, 2))
17
1
30
0
Slices
Named slices
help(slice)
class slice(object)
| slice(stop)
| slice(start, stop[, step])
|
| Create a slice object. This is used for extended slicing
(e.g. a[0:10:2]).
|
| Methods defined here:
|
| __eq__(self, value, /)
| Return self==value.
|
| __ge__(self, value, /)
| Return self>=value.
|
| __getattribute__(self, name, /)
| Return getattr(self, name).
|
| __gt__(self, value, /)
| Return self>value.
|
| __le__(self, value, /)
| Return self<=value.
|
| __lt__(self, value, /)
| Return self<value.
|
| __ne__(self, value, /)
| Return self!=value.
|
| __new__(*args, **kwargs) from builtins.type
| Create and return a new object. See help(type) for
accurate signature.
|
| __reduce__(...)
| Return state information for pickling.
|
| __repr__(self, /)
| Return repr(self).
|
| indices(...)
| S.indices(len) -> (start, stop, stride)
|
| Assuming a sequence of length len, calculate the
start and stop
| indices, and the stride length of the extended slice
described by
| S. Out of bounds indices are clipped in a manner
consistent with the
| handling of normal slices.
|
| ---------------------------------------------------------
-------------
| Data descriptors defined here:
|
| start
|
| step
|
| stop
|
| ---------------------------------------------------------
-------------
| Data and other attributes defined here:
|
| __hash__ = None
if
Conditional Assignment
y = 10
x = 3 if (y == 1) else 2
print(x)
x = 2
x == 2 and 10
10
x = 2
x == 2 and 10 or 5
10
x = 4
x == 2 and 10 or 5
5
Functions
default arguments
def foo(x=[]):
x.append(1)
print(x)
foo()
foo()
foo()
[1]
[1, 1]
[1, 1, 1]
# instead use:
def fun(x=None):
if x is None:
x = []
x.append(1)
print(x)
fun()
fun()
fun()
[1]
[1]
[1]
point_foo = (3, 4)
point_bar = {'y': 3, 'x': 2}
draw_point(*point_foo)
draw_point(**point_bar)
3 4
2 3
Function arguments
def letsEcho():
test = "Hello"
print(test)
letsEcho.test = "Welcome"
print(letsEcho.test)
letsEcho()
Welcome
Hello
def dum_dum():
try:
return '`dum dum` returning from try'
finally:
return '`dum dum` returning from finally'
print(dum_dum())
def my_list(x):
return x, x - 1
print(my_list(10))
result, _ = my_list(10)
(10, 9)
OOPS
Attributes
class Test():
def __getattribute__(self, name):
f = lambda: " ".join([name, name[::-1]])
return f
t = Test()
# New attribute created at runtime
t.rev()
'rev ver'
Operators
x = 5
True
10 < x < 20
False
True
10 > x <= 9
True
5 == x > 4
True
enumerate
Wrap an iterable with enumerate and it will yield the item along
with its index.
0 a
1 b
2 c
3 d
4 e
Generators
Sending values into generator functions
https://www.python.org/dev/peps/pep-0342/, also please reaad
http://www.dabeaz.com/coroutines/
def mygen():
"""Yield 5 until something else is passed back via
send()"""
a = 5
while True:
f = (yield a) #yield a and possibly get f in return
if f is not None:
a = f #store the new value
g = mygen()
print(next(g))
print(next(g))
g.send(7)
print(next(g))
print(next(g))
g.send(17)
print(next(g))
print(next(g))
5
5
7
7
17
17
Descriptor
http://users.rcn.com/python/download/Descriptor.htm
Iterators
def seek_next_line(f):
"""
The iter(callable, until_value) function repeatedly calls
callable and yields its result until until_value is
returned.
"""
for c in iter(lambda: f.read(1),'\n'):
pass
I/O
with
try:
with open('a', 'w') as a, open('b', 'w') as b:
pass
except IOError as e:
print ('Operation failed: %s' % e.strerror)
Re-raising exceptions:
def some_operation():
raise Exception
def is_fatal(e):
return True
# Python 3 syntax
try:
some_operation()
except Exception as e:
if is_fatal(e):
raise
handle_nonfatal(e)
-------------------------------------------------------------
--------------
Exception Traceback (most
recent call last)
<ipython-input-4-18cc95aa93e6> in <module>()
7 # Python 3 syntax
8 try:
----> 9 some_operation()
10 except Exception as e:
11 if is_fatal(e):
<ipython-input-4-18cc95aa93e6> in some_operation()
1 def some_operation():
----> 2 raise Exception
3
4 def is_fatal(e):
5 return True
Exception:
Modules
import os
print(os)
Lets check with the local module. I have created a echo.py file and
now importing and testing on it.
import echo
print(echo)
import __hello__
Hello world!
import codecs
s = 'The Zen of Python, by Tim Peters'
enc = codecs.getencoder( "rot-13" )
dec = codecs.getdecoder("rot-13")
os = enc( s )[0]
print(os)
print(dec(os)[0])