An Introduction tothe Zen of Python
Doug Hellmann February, 2011
Friday, February 18, 2011
The Zen of Pythonby Tim Peters
• Beautiful is better than ugly.• Explicit is better than implicit.• Simple is better than complex.• Complex is better than
complicated.• Flat is better than nested.• Sparse is better than dense.• Readability counts.• Special cases aren't special enough
to break the rules.• Although practicality beats purity.• Errors should never pass silently.• Unless explicitly silenced.• In the face of ambiguity, refuse the
temptation to guess.
• There should be one – and preferably only one – obvious way to do it.
• Although that way may not be obvious at first unless you're Dutch.
• Now is better than never.• Although never is often better than
*right* now.• If the implementation is hard to
explain, it's a bad idea.• If the implementation is easy to
explain, it may be a good idea.• Namespaces are one honking great
idea – let's do more of those!
Friday, February 18, 2011
Beautiful is better than ugly.
• Write programs for human readers
• Simple expression syntax
• Consistent syntax and behavior
Friday, February 18, 2011
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Simple Expressions
Friday, February 18, 2011
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Simple Expressions
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Simple Expressions
1 i = 5 + 5 2 3 s = 'literal string' 4 5 m = """multi-line 6 string 7 """ 8 9 us = u'üñîçø∂é string'10 11 vals = [ 1, 3, 5, 7, ]12 vals[0]
13 14 t = ('a', 1, vals, None) 15 t[1] 16 17 d = { 'a':'a value', 18 'b':'b value', 19 } 20 d['a'] 21 22 if a or b: 23 do_something() 24
Friday, February 18, 2011
Explicit is better than implicit.
• Boolean type
• No “hidden” loop variables
• Use “self” to refer to object inside a method
Friday, February 18, 2011
Boolean Values
1 t = True 2 f = False 3 4 if t: 5 print 't is true' 6 7 if not f: 8 print 'f is false' 9 10 a = t or f 11 b = t and f 12 13 print a 14 print b
$ python booleans.pyt is truef is falseTrueFalse
Friday, February 18, 2011
for loops
1 print 'Numbers:' 2 3 for i in range(5): 4 print i 5 6 print 7 print 'Letters:' 8 9 for c in [ 'a', 'b', 'c' ]: 10 print c
$ python for_loop.py
Numbers:01234
Letters:abc
Friday, February 18, 2011
Defining a Class
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Defining a Class
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Defining a Class
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Defining a Class
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Defining a Class
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Simple is better than complex.
• Garbage collection
• print statement
• Interactive interpreter for experimentation
Friday, February 18, 2011
Printing
1 # -*- encoding: utf-8 -*- 2 3 print 'string:', 'string' 4 5 print 'unicode:', u'üñîçø∂é string' 6 7 print 'number:', 5 * 5 8 9 my_list = [ 1, 'a', None ] 10 print 'list:', my_list 11 12 my_dict = { 'a':'a value', 'b':'b value' } 13 print 'dict:', my_dict
$ python printing.py string: stringunicode: üñîçø∂é stringnumber: 25list: [1, 'a', None]dict: {'a': 'a value', 'b': 'b value'}
Friday, February 18, 2011
Printing, with printf-style Formatting
1 # -*- encoding: utf-8 -*- 2 3 my_list = [ 1, 'a', None ] 4 my_dict = { 'a':'a value', 'b':'b value' } 5 6 args = ('string', u'üñîçø∂é string', 5 * 5, 7 my_list, my_dict) 8 9 print ''' 10 string : %s 11 unicode: %s 12 number : %d 13 list : %s 14 dict : %s 15 ''' % args
$ python printing_with_format.py
string : stringunicode: üñîçø∂é stringnumber : 25list : [1, 'a', None]dict : {'a': 'a value', 'b': 'b value'}
Friday, February 18, 2011
Interactive Interpreter
Friday, February 18, 2011
Complex is better than complicated.
• Do complex things in a “Pythonic” way
• SciPy and NumPy for advanced science and math
Friday, February 18, 2011
Interactive Graphic Environment
SciPy, NumPy, matplotlib
Friday, February 18, 2011
NumPy Performance
1 a = range(10000000) 2 b = range(10000000) 3 c = [] 4 for i in range(len(a)): 5 c.append(a[i] + b[i])
Standard Python 1 import numpy as np 2 a = np.arange(10000000) 3 b = np.arange(10000000) 4 c = a + b
NumPy
5-10 seconds “nearly instantaneous”
Friday, February 18, 2011
Flat is better than nested.
• Wide variety of modules in standard library
• Namespace is flat
• No need to use long names: com.company.java.blah.blah
Friday, February 18, 2011
Standard Library Modules: Networking
• socket
• select
• SocketServer
• BaseHTTPServer
• asyncore
• asynchat
• xmlrpclib
• SimpleXMLRPCServer
Friday, February 18, 2011
Standard Library Modules: Internet Protocols
• urllib
• httplib
• ftplib
• smtpd
• smtplib
• poplib
• imaplib
• json
Friday, February 18, 2011
Standard Library Modules: Command Line
• getopt
• optparse
• argparse
• fileinput
• cmd
• readline
Friday, February 18, 2011
Standard Library Modules: Parallel Processing
• subprocess
• threading
• multiprocessing
• Queue
Friday, February 18, 2011
Standard Library Modules: Databases
• anydbm
• pickle
• shelve
• sqlite3
Friday, February 18, 2011
Standard Library Modules: Miscellaneous
• datetime
• grp
• pwd
• profile
• timeit
• struct
• ctypes
• xml
• tarfile
• csv
Friday, February 18, 2011
Sparse is better than dense.
• Standard library stays “shallow”
• http://pypi.python.org/
• Allows separate release schedules
• pip (“pip installs Python packages”)
Friday, February 18, 2011
Readability counts.
• Whitespace for block structures
• Minimal punctuation
• Built-in documentation
• Extensive online documentation at http://docs.python.org/
Friday, February 18, 2011
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Code Blocks
Friday, February 18, 2011
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Code Blocks
Friday, February 18, 2011
Minimal Punctuation
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Minimal Punctuation
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Inline Documentation
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Inline Documentation
1 class MyClass(object): 2 """Class documentation. 3 """ 4 5 def __init__(self, arg1, arg2): 6 self.attr1 = arg1 7 self.attr2 = arg2 8 9 def do_something(self): 10 """Does some work and returns a value. 11 """ 12 return self.attr1 * self.attr2 13 14 obj = MyClass(1, 2) 15 print obj.do_something()
Friday, February 18, 2011
Special cases aren’t special enough to break the rules.
• Everything is an object
• Methods and functions differ by scope
• Dynamic typing and runtime attribute lookup
• Most “features” in external modules
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
String Methods
1 print ' string value '.split() 2 print ' string value '.strip() 3 print 'str' in ' string value ' 4 print 'CHUGALUG'.startswith('C') 5 print 'CHUGALUG'.endswith('end') 6 print ':'.join(['a', 'b', 'c'])
$ python string_methods.py['string', 'value']string valueTrueTrueFalsea:b:c
Friday, February 18, 2011
Function and Method Scope
1 class MyClass(object): 2 3 def do_something(self, arg1, arg2): 4 return arg1 * arg2 5 6 def my_function(arg1, arg2): 7 return arg1 * arg2
Friday, February 18, 2011
Dynamic Attribute Lookup
1 class MyClass(object): 2 3 CLASS_ATTR = 'class value' 4 5 def __init__(self, arg): 6 self.attr = arg 7 8 o = MyClass('instance value') 9 print o.attr 10 print o.CLASS_ATTR
$ python dynamic_attribute_lookup.pyinstance valueclass value
Friday, February 18, 2011
Dynamic Typing
1 class A(object): 2 def do_something(self): 3 print 'in A' 4 5 class B(object): 6 def do_something(self): 7 print 'in B' 8 9 def work_on_obj(c): 10 c.do_something() 11 12 a = A() 13 b = B() 14 15 work_on_obj(a) 16 work_on_obj(b)
$ python dynamic_typing.pyin Ain B
Friday, February 18, 2011
Regular Expressions
1 import re 2 3 pattern = 'this' 4 text = 'Does this text match the pattern?' 5 6 match = re.search(pattern, text) 7 8 s = match.start() 9 e = match.end() 10 11 print 'Found :', match.re.pattern 12 print 'In :', match.string 13 print 'Range :', s, '-', e 14 print 'Substring:', text[s:e]
$ python using_regex.pyFound : thisIn : Does this text match the pattern?Range : 5 - 9Substring: this
Friday, February 18, 2011
Although practicality beats purity.
• Multiple Programming Models
• OOP
• Procedural
• Functional
Friday, February 18, 2011
Procedural
1 def my_function(arg1, arg2): 2 """This function multiplies arg1 by arg2. 3 """ 4 return arg1 * arg2 5 6 results = [] 7 for i in range(5): 8 results.append(my_function(i, i)) 9 10 print results
$ python procedural.py[0, 1, 4, 9, 16]
Friday, February 18, 2011
Functional: List Comprehension
1 results = [ i*i for i in range(5) ] 2 3 print results
$ python functional.py[0, 1, 4, 9, 16]
Friday, February 18, 2011
Functional: List Comprehension
1 results = [ i*i for i in range(5) ] 2 3 print results
$ python functional.py[0, 1, 4, 9, 16]
Friday, February 18, 2011
Functional: List Comprehension
1 results = [ i*i for i in range(5) ] 2 3 print results
$ python functional.py[0, 1, 4, 9, 16]
Friday, February 18, 2011
Functional: List Comprehension
1 results = [ i*i for i in range(5) ] 2 3 print results
$ python functional.py[0, 1, 4, 9, 16]
Friday, February 18, 2011
Functional: Generator Expression
1 results = ( i*i for i in range(5) ) 2 3 print results 4 5 for i in results: 6 print i
1 $ python generator_expr.py 2 <generator object <genexpr> at 0x1004d20a0> 3 0 4 1 5 4 6 9 7 16
Friday, February 18, 2011
Functional: Generators
1 def gen_values(n): 2 for i in range(n): 3 yield i*i 4 5 print gen_values(5) 6 7 for i in gen_values(5): 8 print i
1 $ python generator.py 2 <generator object gen_values at 0x1004d2050> 3 0 4 1 5 4 6 9 7 16
Friday, February 18, 2011
Errors should never pass silently.
• Exception-based error handling
• Tracebacks aid debugging
Friday, February 18, 2011
Exceptions and Tracebacks
1 def f(n): 2 if n > 0: 3 return n * f(n-1) 4 return 1 5 6 print f('5')
$ python traceback.pyTraceback (most recent call last): File ".../traceback.py", line 6, in <module> print f('5') File ".../traceback.py", line 3, in f return n * f(n-1)TypeError: unsupported operand type(s) for -: 'str' and 'int'
Friday, February 18, 2011
Raising Exceptions
1 def f(n): 2 if not isinstance(n, int): 3 raise TypeError('n should be an int') 4 if n > 0: 5 return n * f(n-1) 6 return 1 7 8 print f('5')
$ python raising.pyTraceback (most recent call last): File ".../raising.py", line 8, in <module> print f('5') File ".../raising.py", line 3, in f raise TypeError('n should be an int')TypeError: n should be an int
Friday, February 18, 2011
Raising Exceptions
1 def f(n): 2 if not isinstance(n, int): 3 raise TypeError('n should be an int') 4 if n > 0: 5 return n * f(n-1) 6 return 1 7 8 print f('5')
$ python raising.pyTraceback (most recent call last): File ".../raising.py", line 8, in <module> print f('5') File ".../raising.py", line 3, in f raise TypeError('n should be an int')TypeError: n should be an int
Friday, February 18, 2011
Unless explicitly silenced.
• Catch exceptions with try:except
• Process
• Convert
• Ignore
Friday, February 18, 2011
Catching Exceptions
1 def f(n): 2 if not isinstance(n, int): 3 raise TypeError('n should be an int') 4 if n > 0: 5 return n * f(n-1) 6 return 1 7 8 try: 9 print f('5') 10 except TypeError, err: 11 print 'Had an error:', err 12 else: 13 print 'No error' 14 finally: 15 print 'Always run'
$ python catching.pyHad an error: n should be an intAlways run
Friday, February 18, 2011
In the face of ambiguity, refuse the temptation to guess.
• Coerce types only when not surprising
• Cannot add strings and numbers
• Can multiply them!
Friday, February 18, 2011
Type Coercion
1 print 5 * 1.0 2 print 2 ** 100 3 print 2 * 'abc' 4 print 2 + 'abc'
1 $ python type_coercion.py 2 5.0 3 1267650600228229401496703205376 4 abcabc 5 Traceback (most recent call last): 6 File ".../type_coercion.py", line 4, in <module> 7 print 2 + 'abc' 8 TypeError: unsupported operand type(s) for +: 'int' and 'str'
Friday, February 18, 2011
Type Coercion
1 print 5 * 1.0 2 print 2 ** 100 3 print 2 * 'abc' 4 print 2 + 'abc'
1 $ python type_coercion.py 2 5.0 3 1267650600228229401496703205376 4 abcabc 5 Traceback (most recent call last): 6 File ".../type_coercion.py", line 4, in <module> 7 print 2 + 'abc' 8 TypeError: unsupported operand type(s) for +: 'int' and 'str'
Friday, February 18, 2011
Type Coercion
1 print 5 * 1.0 2 print 2 ** 100 3 print 2 * 'abc' 4 print 2 + 'abc'
1 $ python type_coercion.py 2 5.0 3 1267650600228229401496703205376 4 abcabc 5 Traceback (most recent call last): 6 File ".../type_coercion.py", line 4, in <module> 7 print 2 + 'abc' 8 TypeError: unsupported operand type(s) for +: 'int' and 'str'
Friday, February 18, 2011
Type Coercion
1 print 5 * 1.0 2 print 2 ** 100 3 print 2 * 'abc' 4 print 2 + 'abc'
1 $ python type_coercion.py 2 5.0 3 1267650600228229401496703205376 4 abcabc 5 Traceback (most recent call last): 6 File ".../type_coercion.py", line 4, in <module> 7 print 2 + 'abc' 8 TypeError: unsupported operand type(s) for +: 'int' and 'str'
Friday, February 18, 2011
Type Coercion
1 print 5 * 1.0 2 print 2 ** 100 3 print 2 * 'abc' 4 print 2 + 'abc'
1 $ python type_coercion.py 2 5.0 3 1267650600228229401496703205376 4 abcabc 5 Traceback (most recent call last): 6 File ".../type_coercion.py", line 4, in <module> 7 print 2 + 'abc' 8 TypeError: unsupported operand type(s) for +: 'int' and 'str'
Friday, February 18, 2011
There should be one – and preferably only one – way to do it.
• Eliminate redundancy
• Easier to learn
• Easier to remember
Friday, February 18, 2011
Index API
1 a = [ 1, 2, 3 ] 2 print a[0] 3 4 a = (1, 2, 3) 5 print a[0] 6 7 a = 'abc' 8 print a[0] 9 10 a = {0:'zero value', 11 1:'one value', 12 } 13 print a[0]
$ python index_api.py11azero value
Friday, February 18, 2011
Although that way may not be obvious at first unless you’re Dutch.
• GUI
• GTK
• KDE
• Cocoa
• MS Windows
• Tk
• wxPython
• Web
• Django
• AppEngine
• Pyramid
• Flask
• TurboGears
• Pecan
Friday, February 18, 2011
Now is better than never.
• ctypes
• Jython
• IronPython
• Python 2 vs. Python 3
Friday, February 18, 2011
Although never is often better than right now.
• Language moratorium
• Not everything goes into stdlib any more
Friday, February 18, 2011
If the implementation is hard to explain, it’s a bad idea. Python Enhancement Proposals
Friday, February 18, 2011
If the implementation is easy to explain, it may be a good idea.
Friday, February 18, 2011
Namespaces are one honking great idea – let’s do more of those!
Closures
Friday, February 18, 2011
Closures
1 def outer(arg): 2 print 'outer(%s)' % arg 3 4 def inner(val): 5 print 'inner(%s) (arg=%s)' % (val, arg) 6 return val * arg 7 8 return inner 9 10 print 'Creating thrice:' 11 thrice = outer(3) 12 13 print '\nCalling thrice:' 14 print thrice(3) 15 print thrice('a')
Friday, February 18, 2011
Closures
1 def outer(arg): 2 print 'outer(%s)' % arg 3 4 def inner(val): 5 print 'inner(%s) (arg=%s)' % (val, arg) 6 return val * arg 7 8 return inner 9 10 print 'Creating thrice:' 11 thrice = outer(3) 12 13 print '\nCalling thrice:' 14 print thrice(3) 15 print thrice('a')
$ python closure.pyCreating thrice:outer(3)
Calling thrice:inner(3) (arg=3)9inner(a) (arg=3)aaa
Friday, February 18, 2011
References
• http://docs.python.org/
• http://www.doughellmann.com/PyMOTW/
• Learning Python by Mark Lutz
• Python Essential Reference by David Beazley
• The Python Standard Library by Example by Doug Hellmann
• http://us.pycon.org/
Friday, February 18, 2011
Questions?
Friday, February 18, 2011
Image Credits
1. http://www.gaialandscapedesignbackgrounds.net/landscape_design_architecture_background_Zen_Garden_chan3.htm
3. http://www.flickr.com/photos/grabadonut/539151245/sizes/l/in/photostream/
13. http://www.flickr.com/photos/tobascodagama/3106398602/
17. http://www.flickr.com/photos/benandliz/11065336/
21 & 22. http://scipy.org
24. http://www.otherlandtoys.co.uk/russian-matryoshka-nesting-dolls-pieces-p-2126.html
32. http://www.dandelionsummers.com/html/building_block.html
36. http://www.flickr.com/photos/photoinference/2494576240/in/faves-40068198@N04/
47. http://www.flickr.com/photos/smithsonian/3112472619/in/faves-40068198@N04/
54. http://www.flickr.com/photos/mherring/3722272868/sizes/l/in/photostream/
57. http://www.webstaurantstore.com/9-3-4-x-4-1-2-unbleached-natural-coffee-filter-12-cup-1000-cs/121CF12U.html
59. http://brainstorm-services.com/wcu-lit/ambiguity.html
66. http://commons.wikimedia.org/wiki/File:Dutch_windmill.jpg
67. http://www.epicpm.org/epic-blogging
68. http://www.skyscanner.net/news/articles/2009/09/002990-travel-tip-10-get-on-last-and-learn-the-art-of-patience.html
69. http://gizmodo.com/5015735/the-top-10-rube-goldberg-machines-featured-on-film
71. http://www.nutricaplabs.com/capsule-manufacturer.aspx
75. http://wmltech.wordpress.com/2006/12/09/got-questions/
Friday, February 18, 2011