diff options
Diffstat (limited to 'fr-fr/python-fr.html.markdown')
-rw-r--r-- | fr-fr/python-fr.html.markdown | 802 |
1 files changed, 523 insertions, 279 deletions
diff --git a/fr-fr/python-fr.html.markdown b/fr-fr/python-fr.html.markdown index 0ae410de..ca510d66 100644 --- a/fr-fr/python-fr.html.markdown +++ b/fr-fr/python-fr.html.markdown @@ -1,293 +1,377 @@ --- -language: python -filename: learnpython-fr.py +language: Python contributors: - - ["Louie Dinh", "http://ldinh.ca"] + - ["Louie Dinh", "http://pythonpracticeprojects.com"] + - ["Steven Basart", "http://github.com/xksteven"] + - ["Andre Polykanine", "https://github.com/Oire"] + - ["Zachary Ferguson", "http://github.com/zfergus2"] translators: - - ["Sylvain Zyssman", "https://github.com/sylzys"] - - ["Nami-Doc", "https://github.com/Nami-Doc"] + - ["Gnomino", "https://github.com/Gnomino"] + - ["Julien M'Poy", "http://github.com/groovytron"] +filename: learnpython-fr.py lang: fr-fr --- -Python a été créé par Guido Van Rossum au début des années 90. C'est maintenant un des langages de programmation les plus populaires. -Je suis tombé amoureux de Python de par la clarté de sa syntaxe. C'est pratiquement du pseudo-code exécutable. +Python a été créé par Guido Van Rossum au début des années 90. C'est maintenant un des +langages les plus populaires. Je suis tombé amoureux de Python pour la clarté de sa syntaxe. +C'est tout simplement du pseudo-code exécutable. -Vos retours sont grandement appréciés. Vous pouvez me contacter sur Twitter [@louiedinh](http://twitter.com/louiedinh) ou par e-mail: louiedinh [at] [google's email service] +L'auteur original apprécierait les retours (en anglais): vous pouvez le contacter sur Twitter à [@louiedinh](http://twitter.com/louiedinh) ou par mail à l'adresse louiedinh [at] [google's email service] -N.B. : Cet article s'applique spécifiquement à Python 2.7, mais devrait s'appliquer pour toute version Python 2.x. Python 2.7 est en fin de vie et ne sera plus maintenu à partir de 2020, il est donc recommandé d'apprendre Python avec Python 3. Pour Python 3.x, il existe un autre [tutoriel pour Python 3](http://learnxinyminutes.com/docs/fr-fr/python3-fr/). +Note : Cet article s'applique spécifiquement à Python 3. Jettez un coup d'oeil [ici](http://learnxinyminutes.com/docs/fr-fr/python-fr/) pour apprendre le vieux Python 2.7 ```python -# Une ligne simple de commentaire commence par un dièse -""" Les lignes de commentaires multipes peuvent être écrites - en utilisant 3 guillemets ("), et sont souvent utilisées - pour les commentaires + +# Un commentaire d'une ligne commence par un dièse + +""" Les chaînes de caractères peuvent être écrites + avec 3 guillemets doubles ("), et sont souvent + utilisées comme des commentaires. """ #################################################### -## 1. Types Primaires et Opérateurs +## 1. Types de données primaires et opérateurs #################################################### -# Les nombres -3 #=> 3 - -# Les calculs produisent les résultats mathématiques escomptés -1 + 1 #=> 2 -8 - 1 #=> 7 -10 * 2 #=> 20 -35 / 5 #=> 7 +# On a des nombres +3 # => 3 -# La division est un peu spéciale. C'est une division d'entiers, et Python arrondi le résultat par défaut automatiquement. -5 / 2 #=> 2 - -# Pour corriger ce problème, on utilise les float. -2.0 # Voici un float -11.0 / 4.0 #=> 2.75 ahhh... beaucoup mieux - -# Forcer la priorité avec les parenthèses -(1 + 3) * 2 #=> 8 - -# Les valeurs booléenes sont de type primitif -True -False +# Les calculs sont ce à quoi on s'attend +1 + 1 # => 2 +8 - 1 # => 7 +10 * 2 # => 20 -# Pour la négation, on utilise "not" -not True #=> False -not False #=> True +# Sauf pour la division qui retourne un float (nombre à virgule flottante) +35 / 5 # => 7.0 -# Pour l'égalité, == -1 == 1 #=> True -2 == 1 #=> False +# Résultats de divisions entières tronqués pour les nombres positifs et négatifs +5 // 3 # => 1 +5.0 // 3.0 # => 1.0 # works on floats too +-5 // 3 # => -2 +-5.0 // 3.0 # => -2.0 -# L'inégalité est symbolisée par != -1 != 1 #=> False -2 != 1 #=> True +# Quand on utilise un float, le résultat est un float +3 * 2.0 # => 6.0 -# D'autres comparateurs -1 < 10 #=> True -1 > 10 #=> False -2 <= 2 #=> True -2 >= 2 #=> True +# Modulo (reste de la division) +7 % 3 # => 1 -# On peut enchaîner les comparateurs ! -1 < 2 < 3 #=> True -2 < 3 < 2 #=> False +# Exponentiation (x**y, x élevé à la puissance y) +2**4 # => 16 -# Les chaînes de caractères sont créées avec " ou ' -"C'est une chaîne." -'C\'est aussi une chaîne.' +# Forcer la priorité de calcul avec des parenthèses +(1 + 3) * 2 # => 8 -# On peut aussi les "additioner" ! -"Hello " + "world!" #=> "Hello world!" - -# Une chaîne peut être traitée comme une liste de caractères -"C'est une chaîne"[0] #=> 'C' +# Les valeurs booléennes sont primitives +True +False -# % peut être utilisé pour formatter des chaîne, comme ceci: -"%s can be %s" % ("strings", "interpolated") +# Négation avec not +not True # => False +not False # => True + +# Opérateurs booléens +# On note que "and" et "or" sont sensibles à la casse +True and False #=> False +False or True #=> True + +# Utilisation des opérations booléennes avec des entiers : +0 and 2 #=> 0 +-5 or 0 #=> -5 +0 == False #=> True +2 == True #=> False +1 == True #=> True + +# On vérifie une égalité avec == +1 == 1 # => True +2 == 1 # => False + +# On vérifie une inégalité avec != +1 != 1 # => False +2 != 1 # => True + +# Autres opérateurs de comparaison +1 < 10 # => True +1 > 10 # => False +2 <= 2 # => True +2 >= 2 # => True + +# On peut enchaîner les comparaisons +1 < 2 < 3 # => True +2 < 3 < 2 # => False + +# (is vs. ==) is vérifie si deux variables pointent sur le même objet, mais == vérifie +# si les objets ont la même valeur. +a = [1, 2, 3, 4] # a pointe sur une nouvelle liste, [1, 2, 3, 4] +b = a # b pointe sur a +b is a # => True, a et b pointent sur le même objet +b == a # => True, les objets a et b sont égaux +b = [1, 2, 3, 4] # b pointe sur une nouvelle liste, [1, 2, 3, 4] +b is a # => False, a et b ne pointent pas sur le même objet +b == a # => True, les objets a et b ne pointent pas sur le même objet + +# Les chaînes (ou strings) sont créées avec " ou ' +"Ceci est une chaine" +'Ceci est une chaine aussi.' + +# On peut additionner des chaînes aussi ! Mais essayez d'éviter de le faire. +"Hello " + "world!" # => "Hello world!" +# On peut aussi le faire sans utiliser '+' +"Hello " "world!" # => "Hello world!" + +# On peut traîter une chaîne comme une liste de caractères +"This is a string"[0] # => 'T' + +# .format peut être utilisé pour formatter des chaînes, comme ceci: +"{} peuvent etre {}".format("Les chaînes", "interpolées") + +# On peut aussi réutiliser le même argument pour gagner du temps. +"{0} be nimble, {0} be quick, {0} jump over the {1}".format("Jack", "candle stick") +#=> "Jack be nimble, Jack be quick, Jack jump over the candle stick" + +# On peut aussi utiliser des mots clés pour éviter de devoir compter. +"{name} wants to eat {food}".format(name="Bob", food="lasagna") #=> "Bob wants to eat lasagna" + +# Il est également possible d'utiliser les f-strings depuis Python 3.6 (https://docs.python.org/3/whatsnew/3.6.html#pep-498-formatted-string-literals) +name = "Fred" +f"Il a dit que son nom est {name}." #=> "Il a dit que son nom est Fred." + +# Si votre code doit aussi être compatible avec Python 2.5 et moins, +# vous pouvez encore utiliser l'ancienne syntaxe : +"Les %s peuvent être %s avec la %s méthode" % ("chaînes", "interpolées", "vieille") -# Une autre manière de formatter les chaînes de caractères est d'utiliser la méthode 'format' -# C'est la méthode à privilégier -"{0} peut être {1}".format("La chaîne", "formattée") -# On peut utiliser des mot-clés au lieu des chiffres. -"{name} veut manger des {food}".format(name="Bob", food="lasagnes") # None est un objet -None #=> None +None # => None -# Ne pas utiliser le symbole d'inégalité "==" pour comparer des objet à None -# Il faut utiliser "is" -"etc" is None #=> False -None is None #=> True +# N'utilisez pas "==" pour comparer des objets à None +# Utilisez plutôt "is". Cela permet de vérifier l'égalité de l'identité des objets. +"etc" is None # => False +None is None # => True -# L'opérateur 'is' teste l'identité de l'objet. -# Ce n'est pas très utilisé avec les types primitifs, mais cela peut être très utile -# lorsque l'on utilise des objets. - -# None, 0, et les chaînes de caractères vides valent False. +# None, 0, and les strings/lists/dicts (chaînes/listes/dictionnaires) valent False lorsqu'ils sont convertis en booléens. # Toutes les autres valeurs valent True -0 == False #=> True -"" == False #=> True +bool(0) # => False +bool("") # => False +bool([]) #=> False +bool({}) #=> False #################################################### ## 2. Variables et Collections #################################################### -# Afficher du texte, c'est facile -print "Je suis Python. Enchanté!" - +# Python a une fonction print pour afficher du texte +print("I'm Python. Nice to meet you!") -# Il n'y a pas besoin de déclarer les variables avant de les assigner. -some_var = 5 # La convention veut que l'on utilise des minuscules_avec_underscores -some_var #=> 5 +# Par défaut, la fonction print affiche aussi une nouvelle ligne à la fin. +# Utilisez l'argument optionnel end pour changer ce caractère de fin. +print("Hello, World", end="!") # => Hello, World! -# Accéder à une variable non assignée lève une exception -# Voyez les structures de contrôle pour en apprendre plus sur la gestion des exceptions. -some_other_var # Lève une exception +# Pas besoin de déclarer des variables avant de les définir. +# La convention est de nommer ses variables avec des minuscules_et_underscores +some_var = 5 +some_var # => 5 -# 'if' peut être utilisé comme expression -"yahoo!" if 3 > 2 else 2 #=> "yahoo!" +# Tenter d'accéder à une variable non définie lève une exception. +# Voir Structures de contrôle pour en apprendre plus sur le traitement des exceptions. +une_variable_inconnue # Lève une NameError -# Listes +# Les listes permettent de stocker des séquences li = [] -# On peut remplir liste dès l'instanciation +# On peut initialiser une liste pré-remplie other_li = [4, 5, 6] -# On ajoute des éléments avec 'append' -li.append(1) #li contient [1] -li.append(2) #li contient [1, 2] -li.append(4) #li contient [1, 2, 4] -li.append(3) #li contient [1, 2, 4, 3] - -# Et on les supprime avec 'pop' -li.pop() #=> 3 et li contient [1, 2, 4] -# Remettons-le dans la liste -li.append(3) # li contient [1, 2, 4, 3] de nouveau. - -# On accède aux éléments d'une liste comme à ceux un tableau. -li[0] #=> 1 -# Le dernier élément -li[-1] #=> 3 - -# Accèder aux indices hors limite lève une exception -li[4] # Lève un 'IndexError' - -# On peut accèder à des rangs de valeurs avec la syntaxe "slice" -# (C'est un rang de type 'fermé/ouvert' pour les plus matheux) -li[1:3] #=> [2, 4] -# Sans spécifier de fin de rang, on "saute" le début de la liste -li[2:] #=> [4, 3] -# Sans spécifier de début de rang, on "saute" la fin de la liste -li[:3] #=> [1, 2, 4] - -# Retirer un élément spécifique dee la liste avec "del" -del li[2] # li contient [1, 2, 3] - -# On peut additionner des listes entre elles -li + other_li #=> [1, 2, 3, 4, 5, 6] - Note: li et other_li existent toujours à part entière +# On ajoute des objets à la fin d'une liste avec .append +li.append(1) # li vaut maintenant [1] +li.append(2) # li vaut maintenant [1, 2] +li.append(4) # li vaut maintenant [1, 2, 4] +li.append(3) # li vaut maintenant [1, 2, 4, 3] +# On enlève le dernier élément avec .pop +li.pop() # => 3 et li vaut maintenant [1, 2, 4] +# Et on le remet +li.append(3) # li vaut de nouveau [1, 2, 4, 3] + +# Accès à un élément d'une liste : +li[0] # => 1 +# Accès au dernier élément : +li[-1] # => 3 + +# Accéder à un élément en dehors des limites lève une IndexError +li[4] # Lève une IndexError + +# On peut accéder à une intervalle avec la syntaxe "slice" +# (c'est un rang du type "fermé/ouvert") +li[1:3] # => [2, 4] +# Omettre les deux premiers éléments +li[2:] # => [4, 3] +# Prendre les trois premiers +li[:3] # => [1, 2, 4] +# Sélectionner un élément sur deux +li[::2] # =>[1, 4] +# Avoir une copie de la liste à l'envers +li[::-1] # => [3, 4, 2, 1] +# Pour des "slices" plus élaborées : +# li[debut:fin:pas] + +# Faire une copie d'une profondeur de un avec les "slices" +li2 = li[:] # => li2 = [1, 2, 4, 3] mais (li2 is li) vaut False. + +# Enlever des éléments arbitrairement d'une liste +del li[2] # li is now [1, 2, 3] + +# On peut additionner des listes +# Note: les valeurs de li et other_li ne sont pas modifiées. +li + other_li # => [1, 2, 3, 4, 5, 6] # Concaténer des listes avec "extend()" -li.extend(other_li) # li vaut maintenant [1, 2, 3, 4, 5, 6] +li.extend(other_li) # Maintenant li contient [1, 2, 3, 4, 5, 6] -# Vérifier l'existence d'un élément dans une liste avec "in" -1 in li #=> True +# Vérifier la présence d'un objet dans une liste avec "in" +1 in li # => True -# Récupérer la longueur avec "len()" -len(li) #=> 6 +# Examiner la longueur avec "len()" +len(li) # => 6 -# Les "tuples" sont comme des listes, mais sont immuables. +# Les tuples sont comme des listes mais sont immuables. tup = (1, 2, 3) -tup[0] #=> 1 -tup[0] = 3 # Lève un 'TypeError' - -# Mais vous pouvez faire tout ceci sur les tuples: -len(tup) #=> 3 -tup + (4, 5, 6) #=> (1, 2, 3, 4, 5, 6) -tup[:2] #=> (1, 2) -2 in tup #=> True - -# Vous pouvez "dé-packager" les tuples (ou les listes) dans des variables -a, b, c = (1, 2, 3) # a vaut maintenant 1, b vaut maintenant 2 and c vaut maintenant 3 -# Sans parenthèses, un tuple est créé par défaut +tup[0] # => 1 +tup[0] = 3 # Lève une TypeError + +# Note : un tuple de taille un doit avoir une virgule après le dernier élément, +# mais ce n'est pas le cas des tuples d'autres tailles, même zéro. +type((1)) # => <class 'int'> +type((1,)) # => <class 'tuple'> +type(()) # => <class 'tuple'> + +# On peut utiliser la plupart des opérations des listes sur des tuples. +len(tup) # => 3 +tup + (4, 5, 6) # => (1, 2, 3, 4, 5, 6) +tup[:2] # => (1, 2) +2 in tup # => True + +# Vous pouvez décomposer des tuples (ou des listes) dans des variables +a, b, c = (1, 2, 3) # a vaut 1, b vaut 2 et c vaut 3 +# Les tuples sont créés par défaut sans parenthèses d, e, f = 4, 5, 6 -# Voyez maintenant comme il est facile d'inverser 2 valeurs -e, d = d, e # d is now 5 and e is now 4 +# Voyez comme il est facile d'intervertir deux valeurs : +e, d = d, e # d vaut maintenant 5 et e vaut maintenant 4 -# Dictionnaires +# Créer un dictionnaire : empty_dict = {} -# Un dictionnaire pré-rempli +# Un dictionnaire pré-rempli : filled_dict = {"one": 1, "two": 2, "three": 3} -# Trouver des valeurs avec [] -filled_dict["one"] #=> 1 +# Note : les clés des dictionnaires doivent être de types immuables. +# Elles doivent être convertibles en une valeur constante pour une recherche rapide. +# Les types immuables incluent les ints, floats, strings et tuples. +invalid_dict = {[1,2,3]: "123"} # => Lève une TypeError: unhashable type: 'list' +valid_dict = {(1,2,3):[1,2,3]} # Par contre, les valeurs peuvent être de tout type. + +# On trouve une valeur avec [] +filled_dict["one"] # => 1 + +# On obtient toutes les clés sous forme d'un itérable avec "keys()" Il faut l'entourer +# de list() pour avoir une liste Note: l'ordre n'est pas garanti. +list(filled_dict.keys()) # => ["three", "two", "one"] -# Récupérer toutes les clés sous forme de liste avec "keys()" -filled_dict.keys() #=> ["three", "two", "one"] -# Note - l'ordre des clés du dictionnaire n'est pas garanti. -# Vos résultats peuvent différer de ceux ci-dessus. -# Récupérer toutes les valeurs sous forme de liste avec "values()" -filled_dict.values() #=> [3, 2, 1] -# Note - Même remarque qu'au-dessus concernant l'ordre des valeurs. +# On obtient toutes les valeurs sous forme d'un itérable avec "values()". +# Là aussi, il faut utiliser list() pour avoir une liste. +# Note : l'ordre n'est toujours pas garanti. +list(filled_dict.values()) # => [3, 2, 1] -# Vérifier l'existence d'une clé dans le dictionnaire avec "in" -"one" in filled_dict #=> True -1 in filled_dict #=> False -# Chercher une clé non existante lève une 'KeyError' -filled_dict["four"] # KeyError +# On vérifie la présence d'une clé dans un dictionnaire avec "in" +"one" in filled_dict # => True +1 in filled_dict # => False -# Utiliser la méthode "get()" pour éviter 'KeyError' -filled_dict.get("one") #=> 1 -filled_dict.get("four") #=> None -# La méthode get() prend un argument par défaut quand la valeur est inexistante -filled_dict.get("one", 4) #=> 1 -filled_dict.get("four", 4) #=> 4 +# L'accès à une clé non-existente lève une KeyError +filled_dict["four"] # KeyError -# La méthode "setdefault()" permet d'ajouter de manière sécuris une paire clé-valeur dans le dictionnnaire -filled_dict.setdefault("five", 5) #filled_dict["five"] vaut 5 -filled_dict.setdefault("five", 6) #filled_dict["five"] is toujours 5 +# On utilise "get()" pour éviter la KeyError +filled_dict.get("one") # => 1 +filled_dict.get("four") # => None +# La méthode get accepte une valeur de retour par défaut en cas de valeur non-existante. +filled_dict.get("one", 4) # => 1 +filled_dict.get("four", 4) # => 4 +# "setdefault()" insère une valeur dans un dictionnaire si la clé n'est pas présente. +filled_dict.setdefault("five", 5) # filled_dict["five"] devient 5 +filled_dict.setdefault("five", 6) # filled_dict["five"] est toujours 5 -# Les sets stockent ... des sets +# Ajouter à un dictionnaire +filled_dict.update({"four":4}) #=> {"one": 1, "two": 2, "three": 3, "four": 4} +#filled_dict["four"] = 4 # une autre méthode + +# Enlever des clés d'un dictionnaire avec del +del filled_dict["one"] # Enlever la clé "one" de filled_dict. + + +# Les sets stockent des ensembles empty_set = set() -# On initialise un "set()" avec tout un tas de valeurs -some_set = set([1,2,2,3,4]) # some_set vaut maintenant set([1, 2, 3, 4]) +# Initialiser un set avec des valeurs. Oui, ça ressemble aux dictionnaires, désolé. +some_set = {1, 1, 2, 2, 3, 4} # some_set est maintenant {1, 2, 3, 4} + +# Comme les clés d'un dictionnaire, les éléments d'un set doivent être immuables. +invalid_set = {[1], 1} # => Lève une TypeError: unhashable type: 'list' +valid_set = {(1,), 1} -# Depuis Python 2.7, {} peut être utilisé pour déclarer un 'set' -filled_set = {1, 2, 2, 3, 4} # => {1 2 3 4} +# On peut changer un set : +filled_set = some_set -# Ajouter plus d'éléments au set -filled_set.add(5) # filled_set contient maintenant {1, 2, 3, 4, 5} +# Ajouter un objet au set : +filled_set.add(5) # filled_set vaut maintenant {1, 2, 3, 4, 5} -# Intersection de sets avec & +# Chercher les intersections de deux sets avec & other_set = {3, 4, 5, 6} -filled_set & other_set #=> {3, 4, 5} +filled_set & other_set # => {3, 4, 5} -# Union de sets avec | -filled_set | other_set #=> {1, 2, 3, 4, 5, 6} +# On fait l'union de sets avec | +filled_set | other_set # => {1, 2, 3, 4, 5, 6} -# Différence de sets avec - -{1,2,3,4} - {2,3,5} #=> {1, 4} +# On fait la différence de deux sets avec - +{1, 2, 3, 4} - {2, 3, 5} # => {1, 4} + +# On vérifie la présence d'un objet dans un set avec in +2 in filled_set # => True +10 in filled_set # => False -# Vérifier l'existence d'une valeur dans un set avec "in" -2 in filled_set #=> True -10 in filled_set #=> False #################################################### -## 3. Structure de contrôle +## 3. Structures de contrôle et Itérables #################################################### -# Initialisons une variable +# On crée juste une variable some_var = 5 -# Voici une condition 'if'. L'indentation est significative en Python ! -# Affiche "some_var est inférieur à 10" +# Voici une condition "si". L'indentation est significative en Python! +# Affiche: "some_var is smaller than 10" if some_var > 10: - print "some_var est supérieur à 10." -elif some_var < 10: # La clause elif est optionnelle - print "some_var iinférieur à 10." -else: # La clause else également - print "some_var vaut 10." + print("some_var is totally bigger than 10.") +elif some_var < 10: # La clause elif ("sinon si") est optionelle + print("some_var is smaller than 10.") +else: # La clause else ("sinon") l'est aussi. + print("some_var is indeed 10.") """ -Les boucles "for" permettent d'itérer sur les listes +Les boucles "for" itèrent sur une liste Affiche: - chien : mammifère - chat : mammifère - souris : mammifère + chien est un mammifère + chat est un mammifère + souris est un mammifère """ for animal in ["chien", "chat", "souris"]: - # On peut utiliser % pour l'interpolation des chaînes formattées - print "%s : mammifère" % animal + # On peut utiliser format() pour interpoler des chaînes formattées + print("{} est un mammifère".format(animal)) """ -"range(number)" retourne une liste de nombres -de 0 au nombre donné +"range(nombre)" retourne un itérable de nombres +de zéro au nombre donné Affiche: 0 1 @@ -295,10 +379,34 @@ Affiche: 3 """ for i in range(4): - print i + print(i) + +""" +"range(debut, fin)" retourne un itérable de nombre +de debut à fin. +Affiche: + 4 + 5 + 6 + 7 +""" +for i in range(4, 8): + print(i) """ -Les boucles "while" boucle jusqu'à ce que leur condition ne soit plus vraie +"range(debut, fin, pas)" retourne un itérable de nombres +de début à fin en incrémentant de pas. +Si le pas n'est pas indiqué, la valeur par défaut est 1. +Affiche: + 4 + 6 + 8 +""" +for i in range(4, 8, 2): + print(i) +""" + +Les boucles "while" bouclent jusqu'à ce que la condition devienne fausse. Affiche: 0 1 @@ -307,66 +415,135 @@ Affiche: """ x = 0 while x < 4: - print x + print(x) x += 1 # Raccourci pour x = x + 1 -# Gérer les exceptions avec un bloc try/except - -# Fonctionne pour Python 2.6 et ultérieur: +# On gère les exceptions avec un bloc try/except try: - # Utiliser "raise" pour lever une exception - raise IndexError("This is an index error") + # On utilise "raise" pour lever une erreur + raise IndexError("Ceci est une erreur d'index") except IndexError as e: - pass # Pass ne prend pas d'arguments. Généralement, on gère l'erreur ici. + pass # Pass signifie simplement "ne rien faire". Généralement, on gère l'erreur ici. +except (TypeError, NameError): + pass # Si besoin, on peut aussi gérer plusieurs erreurs en même temps. +else: # Clause optionelle des blocs try/except. Doit être après tous les except. + print("Tout va bien!") # Uniquement si aucune exception n'est levée. +finally: # Éxécuté dans toutes les circonstances. + print("On nettoie les ressources ici") + +# Au lieu de try/finally pour nettoyer les ressources, on peut utiliser with +with open("myfile.txt") as f: + for line in f: + print(line) + +# Python offre une abstraction fondamentale : l'Iterable. +# Un itérable est un objet pouvant être traîté comme une séquence. +# L'objet retourné par la fonction range() est un itérable. + +filled_dict = {"one": 1, "two": 2, "three": 3} +our_iterable = filled_dict.keys() +print(our_iterable) #=> range(1,10). C'est un objet qui implémente l'interface Iterable + +# On peut boucler dessus +for i in our_iterable: + print(i) # Affiche one, two, three + +# Cependant, on ne peut pas accéder aux éléments par leur adresse. +our_iterable[1] # Lève une TypeError + +# Un itérable est un objet qui sait créer un itérateur. +our_iterator = iter(our_iterable) + +# Notre itérateur est un objet qui se rappelle de notre position quand on le traverse. +# On passe à l'élément suivant avec "next()". +next(our_iterator) #=> "one" + +# Il garde son état quand on itère. +next(our_iterator) #=> "two" +next(our_iterator) #=> "three" + +# Après que l'itérateur a retourné toutes ses données, il lève une exception StopIterator +next(our_iterator) # Lève une StopIteration + +# On peut mettre tous les éléments d'un itérateur dans une liste avec list() +list(filled_dict.keys()) #=> Returns ["one", "two", "three"] #################################################### ## 4. Fonctions #################################################### -# Utiliser "def" pour créer une nouvelle fonction +# On utilise "def" pour créer des fonctions def add(x, y): - print "x vaut %s et y vaur %s" % (x, y) - return x + y # Renvoi de valeur avec 'return' + print("x est {} et y est {}".format(x, y)) + return x + y # On retourne une valeur avec return -# Appeller une fonction avec des paramètres -add(5, 6) #=> Affichet "x is 5 et y vaut 6" et renvoie 11 +# Appel d'une fonction avec des paramètres : +add(5, 6) # => affiche "x est 5 et y est 6" et retourne 11 -# Une autre manière d'appeller une fonction, avec les arguments -add(y=6, x=5) # Les arguments peuvent venir dans n'importe quel ordre. +# Une autre manière d'appeler une fonction : avec des arguments +add(y=6, x=5) # Les arguments peuvent être dans n'importe quel ordre. -# On peut définir une foncion qui prend un nombre variable de paramètres +# Définir une fonction qui prend un nombre variable d'arguments def varargs(*args): return args -varargs(1, 2, 3) #=> (1,2,3) +varargs(1, 2, 3) # => (1, 2, 3) - -# On peut également définir une fonction qui prend un nombre -# variable d'arguments +# On peut aussi définir une fonction qui prend un nombre variable de paramètres. def keyword_args(**kwargs): return kwargs -# Appelons-là et voyons ce qu'il se passe -keyword_args(big="foot", loch="ness") #=> {"big": "foot", "loch": "ness"} +# Appelons la pour voir ce qu'il se passe : +keyword_args(big="foot", loch="ness") # => {"big": "foot", "loch": "ness"} + -# On peut faire les deux à la fois si on le souhaite +# On peut aussi faire les deux à la fois : def all_the_args(*args, **kwargs): - print args - print kwargs + print(args) + print(kwargs) """ all_the_args(1, 2, a=3, b=4) affiche: (1, 2) {"a": 3, "b": 4} """ -# En appellant les fonctions, on peut faire l'inverse des paramètres / arguments ! -# Utiliser * pour développer les paramètres, et ** pour développer les arguments -params = (1, 2, 3, 4) -args = {"a": 3, "b": 4} -all_the_args(*args) # equivaut à foo(1, 2, 3, 4) -all_the_args(**kwargs) # equivaut à foo(a=3, b=4) -all_the_args(*args, **kwargs) # equivaut à foo(1, 2, 3, 4, a=3, b=4) +# En appelant des fonctions, on peut aussi faire l'inverse : +# utiliser * pour étendre un tuple de paramètres +# et ** pour étendre un dictionnaire d'arguments. +args = (1, 2, 3, 4) +kwargs = {"a": 3, "b": 4} +all_the_args(*args) # équivalent à foo(1, 2, 3, 4) +all_the_args(**kwargs) # équivalent à foo(a=3, b=4) +all_the_args(*args, **kwargs) # équivalent à foo(1, 2, 3, 4, a=3, b=4) + +# Retourne plusieurs valeurs (avec un tuple) +def swap(x, y): + return y, x # Retourne plusieurs valeurs avec un tuple sans parenthèses. + # (Note: on peut aussi utiliser des parenthèses) + +x = 1 +y = 2 +x, y = swap(x, y) # => x = 2, y = 1 +# (x, y) = swap(x,y) # Là aussi, rien ne nous empêche d'ajouter des parenthèses + +# Portée des fonctions : +x = 5 + +def setX(num): + # La variable locale x n'est pas la même que la variable globale x + x = num # => 43 + print (x) # => 43 + +def setGlobalX(num): + global x + print (x) # => 5 + x = num # la variable globale x est maintenant 6 + print (x) # => 6 + +setX(43) +setGlobalX(6) + # Python a des fonctions de première classe def create_adder(x): @@ -375,67 +552,78 @@ def create_adder(x): return adder add_10 = create_adder(10) -add_10(3) #=> 13 +add_10(3) # => 13 -# Mais également des fonctions anonymes -(lambda x: x > 2)(3) #=> True +# Mais aussi des fonctions anonymes +(lambda x: x > 2)(3) # => True +(lambda x, y: x ** 2 + y ** 2)(2, 1) # => 5 -# On trouve aussi des fonctions intégrées plus évoluées -map(add_10, [1,2,3]) #=> [11, 12, 13] -filter(lambda x: x > 5, [3, 4, 5, 6, 7]) #=> [6, 7] +# TODO - Fix for iterables +# Il y a aussi des fonctions de base +map(add_10, [1, 2, 3]) # => [11, 12, 13] +map(max, [1, 2, 3], [4, 2, 1]) # => [4, 2, 3] -# On peut utiliser la syntaxe des liste pour construire les "maps" et les "filters" -[add_10(i) for i in [1, 2, 3]] #=> [11, 12, 13] -[x for x in [3, 4, 5, 6, 7] if x > 5] #=> [6, 7] +filter(lambda x: x > 5, [3, 4, 5, 6, 7]) # => [6, 7] + +# On peut utiliser les compréhensions de listes pour de jolies maps et filtres. +# Une compréhension de liste stocke la sortie comme une liste qui peut elle même être une liste imbriquée. +[add_10(i) for i in [1, 2, 3]] # => [11, 12, 13] +[x for x in [3, 4, 5, 6, 7] if x > 5] # => [6, 7] #################################################### ## 5. Classes #################################################### -# Une classe est un objet -class Human(object): - # Un attribut de classe. Il est partagé par toutes les instances de cette classe. +# On utilise l'opérateur "class" pour définir une classe +class Human: + + # Un attribut de la classe. Il est partagé par toutes les instances de la classe. species = "H. sapiens" - # Initialiseur basique + # L'initialiseur de base. Il est appelé quand la classe est instanciée. + # Note : les doubles underscores au début et à la fin sont utilisés pour + # les fonctions et attributs utilisés par Python mais contrôlés par l'utilisateur. + # Les méthodes (ou objets ou attributs) comme: __init__, __str__, + # __repr__ etc. sont appelés méthodes magiques. + # Vous ne devriez pas inventer de noms de ce style. def __init__(self, name): - # Assigne le paramètre à l'attribut de l'instance de classe. + # Assigner l'argument à l'attribut de l'instance self.name = name - # Une méthode de l'instance. Toutes les méthodes prennent "self" comme 1er paramètre. + # Une méthode de l'instance. Toutes prennent "self" comme premier argument. def say(self, msg): - return "%s: %s" % (self.name, msg) + return "{name}: {message}".format(name=self.name, message=msg) - # Une méthode de classe est partagée par toutes les instances. - # On les appelle avec le nom de la classe en premier paramètre + # Une méthode de classe est partagée avec entre les instances + # Ils sont appelés avec la classe comme premier argument @classmethod def get_species(cls): return cls.species - # Une méthode statique est appellée sans référence à une classe ou à une instance + # Une méthode statique est appelée sans référence à une instance ni à une classe. @staticmethod def grunt(): return "*grunt*" -# Instancier une classe +# Instantier une classe i = Human(name="Ian") -print i.say("hi") # Affiche "Ian: hi" +print(i.say("hi")) # affiche "Ian: hi" j = Human("Joel") -print j.say("hello") #Affiche "Joel: hello" +print(j.say("hello")) # affiche "Joel: hello" # Appeller notre méthode de classe -i.get_species() #=> "H. sapiens" +i.get_species() # => "H. sapiens" # Changer les attributs partagés Human.species = "H. neanderthalensis" -i.get_species() #=> "H. neanderthalensis" -j.get_species() #=> "H. neanderthalensis" +i.get_species() # => "H. neanderthalensis" +j.get_species() # => "H. neanderthalensis" # Appeller la méthode statique -Human.grunt() #=> "*grunt*" +Human.grunt() # => "*grunt*" #################################################### @@ -444,45 +632,101 @@ Human.grunt() #=> "*grunt*" # On peut importer des modules import math -print math.sqrt(16) #=> 4.0 +print(math.sqrt(16)) # => 4.0 -# Et récupérer des fonctions spécifiques d'un module +# On peut importer des fonctions spécifiques d'un module from math import ceil, floor -print ceil(3.7) #=> 4.0 -print floor(3.7) #=> 3.0 +print(ceil(3.7)) # => 4.0 +print(floor(3.7)) # => 3.0 -# Récuperer toutes les fonctions d'un module -# Attention, ce n'est pas recommandé. +# On peut importer toutes les fonctions d'un module +# Attention: ce n'est pas recommandé. from math import * -# On peut raccourcir le nom d'un module +# On peut raccourcir un nom de module import math as m -math.sqrt(16) == m.sqrt(16) #=> True +math.sqrt(16) == m.sqrt(16) # => True -# Les modules Python sont juste des fichiers Python ordinaires. -# On peut écrire ses propres modules et les importer. -# Le nom du module doit être le même que le nom du fichier. +# Les modules Python sont juste des fichiers Python. +# Vous pouvez écrire les vôtres et les importer. Le nom du module +# est le nom du fichier. -# On peut trouver quelle fonction et attributs déterminent un module +# On peut voir quels fonctions et objets un module définit import math dir(math) +#################################################### +## 7. Avancé +#################################################### + +# Les générateurs aident à faire du code paresseux (lazy) +def double_numbers(iterable): + for i in iterable: + yield i + i + +# Un générateur crée des valeurs à la volée. +# Au lieu de générer et retourner toutes les valeurs en une fois, il en crée une à chaque +# itération. Cela signifie que les valeurs supérieures à 30 ne seront pas traîtées par +# double_numbers. +# Note : range est un générateur aussi. +# Créer une liste 1-900000000 prendrait beaucoup de temps +# On met un underscore à la fin d'un nom de variable normalement réservé par Python. +range_ = range(1, 900000000) +# Double tous les nombres jusqu'à ce qu'un nombre >=30 soit trouvé +for i in double_numbers(range_): + print(i) + if i >= 30: + break + + +# Decorateurs +# Dans cet exemple, beg enveloppe say +# Beg appellera say. Si say_please vaut True le message retourné sera changé +from functools import wraps + + +def beg(target_function): + @wraps(target_function) + def wrapper(*args, **kwargs): + msg, say_please = target_function(*args, **kwargs) + if say_please: + return "{} {}".format(msg, "Please! I am poor :(") + return msg + + return wrapper + + +@beg +def say(say_please=False): + msg = "Can you buy me a beer?" + return msg, say_please + + +print(say()) # affiche Can you buy me a beer? +print(say(say_please=True)) # affiche Can you buy me a beer? Please! I am poor :( ``` -## Prêt à aller plus loin? +## Prêt pour encore plus ? -### En ligne gratuitement +### En ligne et gratuit (en anglais) +* [Automate the Boring Stuff with Python](https://automatetheboringstuff.com) * [Learn Python The Hard Way](http://learnpythonthehardway.org/book/) * [Dive Into Python](http://www.diveintopython.net/) -* [The Official Docs](http://docs.python.org/2.6/) +* [Ideas for Python Projects](http://pythonpracticeprojects.com) +* [The Official Docs](http://docs.python.org/3/) * [Hitchhiker's Guide to Python](http://docs.python-guide.org/en/latest/) -* [Python Module of the Week](http://pymotw.com/2/) +* [A Crash Course in Python for Scientists](http://nbviewer.ipython.org/5920182) +* [Python Course](http://www.python-course.eu/index.php) +* [First Steps With Python](https://realpython.com/learn/python-first-steps/) + +### En ligne et gratuit (en français) -### Format papier +* [Le petit guide des batteries à découvrir](https://he-arc.github.io/livre-python/) + +### Livres (en anglais) * [Programming Python](http://www.amazon.com/gp/product/0596158106/ref=as_li_qf_sp_asin_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596158106&linkCode=as2&tag=homebits04-20) * [Dive Into Python](http://www.amazon.com/gp/product/1441413022/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=1441413022&linkCode=as2&tag=homebits04-20) * [Python Essential Reference](http://www.amazon.com/gp/product/0672329786/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0672329786&linkCode=as2&tag=homebits04-20) - |