Un lenguaje que no afecta tu manera de pensar sobre la programación, no merece ser aprendido.
Así se itera en muchos lenguajes
for (i=0; i < mylist_length; i++) { do_something(mylist[i]); }
Esto es "python"
i = 0 while i < len(mylist): do_something(mylist[i]) i += 1
Buuuh!
for i in range(len(mylist)): do_something(mylist[i])
Ok, dale que va queriendo
Esto es Python
for element in mylist: do_something(element)
Simple is better than complex. Beautiful is better than ugly.
>>> import this
No es sólo un huevo de pascua
Es la guía filosófica de la pythonicidad
la guía de estilo de codificación.
Programs must be written for people to read, and only incidentally for machines to execute.
flake8 FTW! (en el editor o como VCS hook)
pip install isort
Es más fácil pedir perdón que pedir permiso
def f(animal): if isinstance(animal, Duck): animal.quack() else: print("%s can't quack" % animal) def f(animal): try: animal.quack() except (AttributeError, TypeError): print("%s can't quack" % animal)
Lo triste es que esta pobre gente trabajó mucho más de lo necesario, para producir mucho más código del necesario, que funciona mucho más lento que el código python idiomático equivalente.
La mayoría de las veces no hacen falta
x1 = p.get_x() # buuh p.set_x(x1) x1 = p.x p.x = x1
Cuando de verdad hacen falta, se pueden definir con property
@property def edad(self): return (date.today() - self.fecha_nacimiento).days / 365 >>> p.edad 31
if x > 0 and x < 100: # buuh ... if 0 < x < 100: ...
Otra
if x == 0 or x == 2 or x == 4: .... if x in (0, 2, 4):
Expresiones condicionales (operador ternario)
if condition: a = x else: a = y a = x if condition else y
Unir cadenas
names = ['x-ip', 'facundobatista', 'nessita', 'lipe_p'] s = names[0] for name in names[1:]: s += ', ' + name s = ', '.join(names)
Packing/Unpacking (asignación múltiple)
p = u'Martín', u'Gaitán', 31 fname = p[0] # buuhh lname = p[1] age = p[2] fname, lname, age = p
en python 3 el unpacking es mucho más poderoso
Packing/Unpacking 2
def fibonacci(n): x, y = 0, 1 for i in xrange(n): yield x # btw, yield x, y = y, x + y
No muevas los datos innecesariamente
Construir diccionarios desde secuencias
names = ['raymond', 'rachel', 'matthew'] colors = ['red', 'green', 'blue'] d = dict(zip(names, colors)) {'matthew': 'blue', 'rachel': 'green', 'raymond': 'red'}
Listas por comprehensión / Expresiones generadoras
result = [] for i in range(10): if i % 2 == 0: s = i ** 2 result.append(s) sum(result) sum([i**2 for i in xrange(10) if i % 2 == 0]) sum(i**2 for i in xrange(10) if i % 2 == 0)
La legibilidad cuenta: usá los kwargs
twitter_search('#PyconAr2013', False, 20, True) twitter_search('#PyconAr', retweets=False, numtweets=20, popular=True)
La legibilidad cuenta: namedtuple
>>> doctest.testmod() (0, 4) from collections import namedtuple TestResults = namedtuple('TestResults', ['failed', 'attempted']) >>> doctest.testmod() TestResults(failed=0, attempted=4)
collections tiene estructuras buenísimas
Son muy útiles!
engineers = {'John', 'Jane', 'Jack', 'Janice'} programmers = {'Jack', 'Sam', 'Susan', 'Janice'} managers = {'Jane', 'Jack', 'Susan', 'Zack'} employees = engineers | programmers | managers # union fulltime_management = managers - engineers - programmers # difference engineering_management = engineers & managers # intersection >>> engineering_management set(['Jane', 'Jack'])
Decoradores: factorizá lo administrativo
def web_lookup(url, saved={}): if url in saved: return saved[url] page = urllib.urlopen(url).read() saved[url] = page return page @cache def web_lookup(url): return urllib.urlopen(url).read()
Contextos: sentencia with
@contextmanager def tag(name): print("<%s>" % name) yield print("</%s>" % name) >>> with tag("h1"): ... print("foo")
py3 tiene ContextDecorator que es una clase que funciona como decorador o administrador de contexto.
Bucles anidados
combs = [] for a in x: for b in y: for c in z: combs.append((a, b, c)) combs = itertools.product(x, y, z)
itertools es groso!
Para discutir después...
blocks = [] while True: block = f.read(32) if block == '': break blocks.append(block) blocks = [] for block in iter(partial(f.read, 32), ''): blocks.append(block)
un código demasiado avanzado puede ser críptico para otros programadores es elegante pero no más rápido. Al menos requiere un comentario
Space | Forward |
---|---|
Left, Down, Page Down | Next slide |
Right, Up, Page Up | Previous slide |
P | Open presenter console |
H | Toggle this help |