Cours d’Informatique Scientifique
Programmation en Python Cours 6
Laurent Pointal
laurent.pointal @ limsi.fr
@ laposte.net
Programme de la séance
● Pratique... les listes en compréhension
● Traitement des erreurs
● Détection
● Signalisation
● Remontée
– Les exceptions
● Types utiles
● Séquences tuple, ensembles set, dictionnaires dict
● Module collections
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 3 22
v2.2
Construction de listes
Liste existante
Nouvelle liste Calcul et/ou sélection
sur chaque élément
Pour le moment:
●
définition des listes par les valeurs contenues ("en extension"):
lst1 = [1,6,9,2,7,4,12,11,21,4]
●
construction de nouvelle liste par boucle for :
res = []
for v in itérable:
if condition(v) :
res.append(calcul(v))
# liste des carrés des impairs
lst2 = []
for v in lst1:
if v%2==1 :
lst2.append(v**2)
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 4 22
v2.2
Listes en compréhension - syntaxe
Définition des listes par une expression (en “intension” ou “compréhension”)
À partir d’une séquence de valeurs, créer une nouvelle séquence...
res = [ calcul(v) for v in itérable ]
...et on peut enchaîner les niveaux de boucles...
res = [ calcul(v) for v in itérable if condition(v) ] ...avec un filtrage...
res = [ calcul(v1,v2)
for v1 in itérable1
for v2 in itérable2
if condition(x) ]
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 5 22
v2.2
Listes en compréhension - ex. 1 (sans)
# Exemple: lst2 = carrés des nombres de lst1 lst1 = [1,6,9,2,7,4,12,11,21,4]
lst2 = []
for v in lst1:
lst2.append(v**2)
# Exemple: lst2 = carrés des nombres impairs de lst1 lst1 = [1,6,9,2,7,4,12,11,21,4]
lst2 = []
for v in lst1:
if v%2==1:
lst2.append(v**2)
lst2 = v 2 ∀ v ∈ lst1
lst2 = v 2 ∀ v ∈ lst1 si v impair
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 6 22
v2.2
Listes en compréhension - ex. 1 (avec)
# Exemple: lst2 = carrés des nombres de lst1 lst1 = [1,6,9,2,7,4,12,11,21,4]
lst2 = []
for v in lst1:
lst2.append(v**2)
lst2 = [ v**2 for v in lst1 ]
# Exemple: lst2 = carrés des nombres impairs de lst1 lst1 = [1,6,9,2,7,4,12,11,21,4]
lst2 = []
for v in lst1:
if v%2==1:
lst2.append(v**2)
lst2 = [ v**2 for v in lst1 if v%2==1 ]
lst2= v 2 ∀v ∈ lst1
lst2= v 2 ∀v ∈lst1 si v impair
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 7 22
v2.2
Listes en compréhension - ex. 2
res = [x*y for x in range(1,5) for y in range(1,5) if x!=y]
[2, 3, 4, 2, 6, 8, 3, 6, 12, 4, 8, 12]
Exemple : produits xy avec x et y de 1 à 4 et x≠y
res = []
for x in range(1,5):
for y in range(1,5):
if x!=y:
res.append(x*y)
[2, 3, 4, 2, 6, 8, 3, 6, 12, 4, 8, 12]
●
Avec deux boucles imbriquées:
●
Avec une liste en compréhension:
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 8 22
v2.2
Listes en compréhension - ex. autres
Note: pas essentiel à retenir (on peut s’en passer), mais peut être pratique.
lstpoints = [(1,3),(9,2),(7,7),(8,4),(6,11),(3,9) ] max( [ pt[1] for pt in lstpoints ] )
Utilisation très courante pour éviter certaines boucles simples
Exemple, calcul de l’ordonnée max d’une liste de points:
Exemple, somme des cubes des 20 premiers nombres multiples de 7:
sum( [ x**3 for x in range(7,7*20+1,7)] )
Permet d'écrire certaines opérations sur des ensembles
comme dans certains logiciels de calcul en ingénierie.
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 9 22
v2.2
Les erreurs - 1
● La détection
●
Tout vérifier vs Laisser faire
– Un juste milieu
●
Débogage vs Utilisation normale
● Le traitement
●
Signaler l'erreur (à l'utilisateur)
– Utilisateur ciblé (développeur?)
– Précision des informations, pertinence
●
Remonter l'erreur (au programme)
– Valeur de retour de fonction
– Levée d'exception
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 10 22
v2.2
Les erreurs - 2 - Détection
●
Tout vérifier ?
●
Non: Python détecte déjà certaines erreurs
●
Laisser faire ?
●
Oui/Non: Détecter là où il y a des risques de mauvaise utilisation
if 0<=index<len(lst):
v = lst[index]
else:
# Hors limites (on verra que faire ici)
= Généralement inutile
def perimetre_triangle(c0,c1,c2):
cotes = sorted([c0,c1,c2])
if cotes[2] > cotes[0]+cotes[1]:
# Pas un triangle (on verra que faire ici)
return c0+c1+c2
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 11 22
v2.2
Les erreurs - 3 - Débogage
Définis en mode débogage Python:
●
Variable globale booléenne __debug__
●
Instruction assert condition,"message"
option Python -O pour retirer le débogage
Vérifier:
●
Les paramètres en entrée, les valeurs calculées, les valeurs retournées
●
Contraintes ? a > 0 len(lst)>=2
●
Relations ? a > b a in lst
Distinguer :
●
Ce qui relève du débogage de votre code
➔
vérifications actives uniquement en mode débogage
●
Ce qui peut arriver lorsque quelqu'un utilise vos fonctions
➔
vérifications actives tout le temps
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 12 22
v2.2
Les erreurs - 4 - Exemple Débogage
ARTICLES_RECONNUS = ["le","la","les", (...)]
def articles(phrase):
"Retourne la liste des articles présents dans une phrase"
assert type(phrase)==type("")
if len(phrase) == 0: # Chaine vide
print("Erreur: paramètre phrase vide pour articles()") return None # Pour signaler un problème
lart = []
lmots = phrase.lower().split() for mot in lmots:
if mot in ARTICLES_RECONNUS:
if mot not in lart:
lart.append(mot)
# Vérification de l'algorithme
if __debug__: # Pour éviter la boucle hors débug for a in lart:
assert a in ARTICLES_RECONNUS,"article extraterrestre"
assert a in lmots,"mot extrarterrestre"
return lart
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 13 22
v2.2
Les erreurs - 5 - Signalement
●
Signaler l'erreur
●
affichage print("Erreur: Ca va pas!")
– pratique pour débogger / signaler à l'utilisateur
●
journaux logger.error("Ca va pas!")
– système de filtrage (niveaux debug / info / warning / error / critical...)
– système d'enregistrement (print, fichier texte, syslog, serveur sur réseau...)
– système de formatage (ajout date/heure, thread, utilisateur...)
●
Dès qu'elle est détectée
●
en indiquant quoi / comment / ou / pourquoi...
●
en donnant de l'information lisible
– code numérique d'erreur => compléter par message
texte pour l'utilisateur
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 14 22
v2.2
Les erreurs - 6 - Remontée
Problème : comment signaler au code appelant une fonction qu'il y a eu une erreur.
res = fonction1(paramsf1)
# utilisation de res
def fonction1(parametresf1):
...
y = fonction2(paramsf2) z = ...y...
return z
def fonction2(parametresf2):
...
q = fonction3(paramsf3) r = ...q...
return r
def fonction3(parametresf3):
k = ...
return k
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 15 22
v2.2
Les erreurs - 7 - Remontée "code d'erreur"
●
Retour de valeur
●
en cas de problème, retourner une valeur spécifique, un « drapeau » (ex. None)
●
Problèmes
●
définir des codes, les identifier par rapport aux valeurs normales, homogénéiser les codes
entre les différents modules utilisés
●
traiter systématiquement les erreurs dans chaque fonction (risque d'oubli) et les faire remonter
●
mélanger le code normal et le code de
traitement d'erreur (lourdeur, bugs)
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 16 22
v2.2
Les erreurs - 8 - Exceptions
try:
except (exceptions) as e:
répétable avec différents types
d’exceptions
Détection d’une situation d’erreur pendant l'exécution
du bloc ‘try’
[*]: levée d'exception
Une instruction raise seule, exécutée dans le bloc except, remonte l’exception au traitement des erreurs suivant le plus récent.
Quelques classes d'erreurs: Exception ValueError NameError IndexError KeyError AttributeError IOError TypeError ZeroDivisionError…
Bloc ‘try’ exécuté dans les cas normaux.
Bloc exécuté si une
erreur de type exception est détectée.
raise exception("pb")
[*] Éventuellement dans une fonction d'un autre module appelée lors de
cette exécution.
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 17 22
v2.2
Les erreurs - 9 - Exemple Exception
try:
res = fonction1(paramsf1) # utilisation de res
except Exception as err:
print("Erreur", err)
def fonction1(parametresf1):
...
y = fonction2(paramsf2) z = ...y...
return z def fonction2(parametresf2):
try:
q = fonction3(paramsf3) r = ...q...
return r
except Exception as e:
#nettoyage raise
def fonction3(parametresf3):
if ...:
raise ValueError("Bad param") k = ...
return k
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 18 22
v2.2
Les erreurs - 10 - Exemple
from math import sqrt
def perimetre_triangle(c0,c1,c2):
# Contrôle qu'on a un triangle possible cotes = sorted([c0,c1,c2])
if cotes[2] > cotes[0]+cotes[1]:
raise ValueError("pas un triangle") return c0+c1+c2
def aire_triangle(c0,c1,c2):
p = perimetre_triangle(c0,c1,c2)
a = sqrt(p*(p-c1)*(p-c2)*(p-c3)/16)
return a
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 19 22
v2.2
Les séquences tuple
Par rapport aux listes:
●
non modifiable !
●
pas de méthodes de recherche & Co Construction:
●
directement, simplement: t = 1,3,8,0,2,"coucou"
●
directement, avec des parenthèses:
t = (1,3,8,0,2,"coucou") Opérations
●
accès aux valeurs par indexation: t[3]
●
boucles sur les éléments: for elem in t: ...
Où les utiliser ?
●
créés automatiquement: affectation multiple, passage de paramètres...
●
lorsque besoin de regrouper des valeurs qui doivent rester
cohérentes ensembles
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 20 22
v2.2
Les ensembles set
Par rapport aux listes:
●
Chaque élément présent une seule fois, éléments "hashables"
●
Pas d'ordre dans les éléments
●
Test de présence/absence très rapide Construction:
●
directement: ens = {1,3,8,0,2,"coucou"}
●
à partir d'une liste: ens = set([])
●
au fur et à mesure en remplissant / modifiant l'ensemble Modification:
●
création vide: ens = set()
●
ajout: ens.add("élément")
●
suppression: ens.remove(8)
●
mise à jour: ens.update({9,2,21,42,"bof",11}) Opérations
●
cf exemples script
●
boucles sur les éléments: for elem in ens: ...
Il existe aussi frozenset() qui n'est plus modifiable une fois créé.
urent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 21 22
v2.2
Les dictionnaires dict
●
Associations (map) clé => valeur
●
Contraintes:
●
Chaque clé est présente une seule fois
●
Clés "hashables" (ex. pas de liste)
●
Les plus
●
Accès rapide par clé
(comme les ensembles)●
N'importe quelle valeur
Construction
●
directement: dico = {"x":1.2,"nom":"toto",3.14:"pi"}
●
à partir d'une liste: dico = dict([("x",1.2),("nom","toto")])
●
au fur et à mesure en remplissant / modifiant l'ensemble Modification
●
stockage/modification d'association: dico["y"] = 11.7
●
suppression d'association: del dico["y"]
Opérations
●
vues itérables sur clés / éléments / associations: for k in dico /
for k in dico.keys() / for v in dico.values() / for (k,v) in dico.items()
●
test de présence/absence de clé: "x" in dico
●
etc
aurent PointalDépartement Mesures Physiques Cours d’Informatique Scientifique 6/8 22 22
v2.2