#!/usr/bin/env python
# coding: utf-8
# In[1]:
implementations = ['cpython', 'pypy', 'jython', 'ironpython']
for implementation in implementations:
print(implementation)
#
#
#
La philosophie de l'itération
#
#
#
#
#
#
#
kevin@formationspython.com
#
#
#
# # Un design pattern : iterator
# Eviter de boucler à la main:
#
# ```c
# const char *relatedTopics[] = {
# "++",
# "jerome",
# "pas ma faute",
# NULL
# };
#
# for (int i=0; relatedTopics[i]; ++i) {
# const char *ch = relatedTopics[i];
# while(*ch) {
# putchar(*ch++);
# putchar('\n');
# }
# putchar('\n');
# }
#
# ```
#
#
# # Visitor
#
# Methode `forEach` des arrays en JS:
#
# ```javascript
# var nope = ["==", "with", "eval"];
# nope.forEach((e) => {
# console.log(e)
# });
# ```
#
# "L'iterator" `each` de Ruby:
#
# ```Ruby
# popularProjects = ["RoR", "rails", "Ruby on Rails"];
# popularProjects.each do |i|
# puts i
# end
# });
# ```
#
# # Comment Python fait marcher tout ça
# In[2]:
cris = ['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo']
# cris = set(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
# cris = tuple(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
# cris = dict.fromkeys(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
print(f"{type(cris)} de cris :")
for cri in cris:
print(cri, '!')
# In[3]:
cris = ['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo']
#cris = set(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
#cris = tuple(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
#cris = dict.fromkeys(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo'])
# In[4]:
sauce_magique = iter(cris)
# In[5]:
type(sauce_magique)
# In[6]:
next(sauce_magique)
# In[7]:
next(sauce_magique)
# In[8]:
next(sauce_magique)
# In[10]:
next(sauce_magique)
# # Iterator, l'interface universelle
# In[11]:
for i in range(1, 4):
print(i)
# In[12]:
for lettre in "abc":
print(lettre)
# In[13]:
for ligne in open('answers.txt'):
print(ligne)
# In[14]:
list(open('answers.txt'))
# In[15]:
tuple(range(1, 4))
# In[16]:
set('abc')
# In[17]:
sum([1, 2, 3])
# In[18]:
sum(set([1, 2, 3]))
# In[19]:
sum(range(1, 4))
# In[20]:
sum(map(int, "123"))
# In[21]:
sorted(set(['Cowabunga', 'Yippee ki-yay, mofo', 'Wololo']))
# In[22]:
list(filter(bool, (True, False, None, 1, 0)))
# In[23]:
"/////////////".join(open('answers.txt'))
# In[24]:
for i, ligne in enumerate('abc', 1):
print(i, ligne)
# In[79]:
import collections # amis des itérables
collections.Counter('dkjflchldkfhjdlskqfvdkfdhqkj')
# collections.deque
# collections.defaultdict
# collections.OrderedDict
# collections.namedtuple
# In[36]:
# Prend n'importe quel itérable
print(any([True, True, False, True, False]))
print(all([True, True, False, True, False]))
print(max([5, 10, 4, 1]))
# min
# reduce
# Retourne des itérables:
#
# - bytes
# - csv.reader
# - os.walk
# - multiprocessing.Pool.map
# - sqlite3.cursor
# - xml.etree.ElementTree
#
#
# Et même les libs externes:
#
# - Querysets des ORMs (Django, SQLAlchemy, Peewee...);
# - Body des réponses de WSGI
# ## Un module juste pour les itérables
#
#
#
# ```python
# import itertools
#
# itertools.accumulate
# itertools.chain
# itertools.combinations
# itertools.combinations_with_replacement
# itertools.compress
# itertools.count
# itertools.cycle
# itertools.dropwhile
# itertools.filterfalse
# itertools.groupby
# itertools.islice
# itertools.permutations
# itertools.product
# itertools.repeat
# itertools.starmap
# itertools.takewhile
# itertools.tee
# itertools.zip_longest
# ```
# In[39]:
import itertools
for x in itertools.chain('abc', range(3)):
print(x)
# In[40]:
list(itertools.product('abc', range(3)))
# In[41]:
histoire_de_la_vie = iter(itertools.cycle('abc'))
print(next(histoire_de_la_vie))
print(next(histoire_de_la_vie))
print(next(histoire_de_la_vie))
print(next(histoire_de_la_vie))
# ## L'unpacking
# In[25]:
x, y = (1, 2)
print(x)
# In[26]:
def point():
return 1, 2
x, y = point()
print(y)
# In[27]:
a, b, c = ["Aligator", "Behemot", "Claude"]
print(f'a = {a}')
print(f'b = {b}')
print(f'c = {c}')
# In[28]:
a, b, c = open('answers.txt')
print(f'a = {a}')
print(f'b = {b}')
print(f'c = {c}')
# In[29]:
a, *b, d = range(100)
print(f'a = {a}')
print(f'b = {b}')
print(f'd = {d}')
# In[30]:
print(*'abc', sep="#") # équivaut à print("a", "b", "c", sep="#")
# In[31]:
[*range(3), *open('answers.txt'), *set(cris)] # marche aussi pour merger des dictionnaires avec ** :)
# In[15]:
pixels = ["rouge", "vert", "bleu", "rouge", "vert", "bleu", "rouge", "vert", "bleu"]
# In[16]:
pixels[::3], pixels[2::3] = pixels[2::3], pixels[::3]
# In[17]:
pixels
# # Le flux de données
# In[42]:
import subprocess
res = subprocess.check_output(["ifconfig"], encoding="utf8") # devinez ce qu'attend "call" en paramètre ?
print(res)
# In[43]:
import re, subprocess
res = subprocess.check_output(["ifconfig"], encoding="utf8")
reg = re.compile(r'(\S+).*\n.*adr:(\S+)')
# In[44]:
interfaces = {}
for block in res.split('\n\n'):
if 'adr' in block:
interface, ip = reg.match(block).groups()
interfaces[interface] = ip
print(interfaces)
# In[45]:
interfaces = [reg.match(block).groups() for block in res.split('\n\n') if 'adr' in block]
dict(interfaces)
# ## Les intensions
# In[46]:
[x * x for x in range(10)]
# In[47]:
{x: x * x for x in range(10)}
# In[48]:
{x * x for x in range(10)}
# ## Les expressions génératrices
# In[49]:
# NOPE !
# res = [x * x for x in range(10000000000000)]
# In[50]:
res = (x * x for x in range(10000000000000))
# In[51]:
res
# In[52]:
next(res)
# In[53]:
next(res)
# In[54]:
print(next(res))
print(next(res))
print(next(res))
# In[55]:
import sqlite3
def get_results(n=10, profile="/home/pycon/.mozilla/firefox/l92ue2kx.default/places.sqlite"):
return sqlite3.connect(profile).execute("""
SELECT sites.rev_host as host, count(*) as visits FROM moz_historyvisits as visits, moz_places as sites
WHERE visits.place_id == sites.id GROUP BY host ORDER BY visits DESC
""")
# In[56]:
sites = ((dom[-2::-1], vis) for dom, vis in get_results())
# In[57]:
MOTEURS = set(['duckduckgo', 'google', 'bing', 'qwant'])
sites = ((dom, vis) for dom, vis in sites if not any(m in dom for m in MOTEURS))
# In[58]:
import itertools
sites = itertools.islice(sites, 0, 5)
# In[59]:
sites
# In[60]:
next(sites)
# In[61]:
next(sites)
# In[62]:
for s in sites:
print(s)
# ## Yield
# In[63]:
def fonction_normale():
print('Avant le premier return')
return 1
print('Apres le premier return')
return 2
print("Apres le second return")
return 3
print('Tout à la fin')
res = fonction_normale()
print(res)
# In[64]:
def fabriquer_un_generateur():
print('Avant le premier yield')
yield 1
print('Apres le premier yield')
yield 2
print("Apres le second yield")
yield 3
print('Tout à la fin')
res = fabriquer_un_generateur()
print(res)
# In[65]:
next(res)
# In[66]:
next(res)
# In[67]:
for x in res:
print(x)
# In[68]:
import secrets
def secret_key_generator(n):
for i in range(n):
yield secrets.token_hex()
gen = secret_key_generator(10)
# In[69]:
next(gen)
# In[70]:
next(gen)
# In[71]:
import itertools
class MachineAtuer:
def __iter__(self):
while True:
yield "Miaou !"
for x in itertools.islice(MachineAtuer(), 10):
print(x)
# ## Tous les tuyaux mis bouts à bouts
# In[72]:
import string
from pathlib import Path
def lister_mots_cles(dossier, ext):
for chemin in Path(dossier).glob(f'./**/*.{ext}'): # iterable
try:
with open(chemin) as f:
for ligne in f: # iterable
for mot in ligne.split(): # iterable
# expression generatrice sur un itérable passée à join... qui attend un itérable
mot = "".join(l for l in mot if l not in string.punctuation).strip()
if mot:
# génération de données
yield mot
except Exception:
pass
# In[73]:
from collections import Counter
# Counter accepte un itérable en a paramètre
for mot, score in Counter(lister_mots_cles('/etc', 'conf')).most_common(5): # itérable
print(f'- {mot}: {score}')
# In[18]:
get_ipython().run_cell_magic('HTML', '', '\n')
#
#
# In[74]:
import numpy as np # ou scipy, pandas, etc
import matplotlib.pyplot as plt
x = np.arange(0, 3 * np.pi, 0.1)
y = np.sin(x)
plt.plot(x, y)
plt.show()
# In[75]:
import math
x = np.arange(0, 3 * np.pi, 0.1)
get_ipython().run_line_magic('timeit', '[math.sin(i) for i in x]')
get_ipython().run_line_magic('timeit', 'np.sin(x)')
# # Il y a un "one more thing" pour ça
# In[76]:
def crieur():
while True:
res = yield
print(res.upper(), '!')
gen = crieur()
next(gen)
# In[77]:
interdits = [
'les interdictions',
'les listes',
'les interdictions',
'les repetitions',
'les mets',
'les blagues faciles'
]
for x in interdits:
gen.send(x)
#
# Télécharger les slides
#
#
#
# https://huit.re/philo-iteration-fr
#
#
#
#
#
# kevin@formationspython.com
#