Mettre en boîte notre code
Fini, l'interpréteur ?
Je le répète encore, l'interpréteur est véritablement très pratique pour un grand nombre de raisons. Et la meilleure d'entre elles est qu'il propose une manière interactive d'écrire un programme avec la possibilité de tester à chaque instruction le résultat. Toutefois, l'interpréteur a aussi un défaut : le code que vous entrez est effacé à la fermeture de la fenêtre. Or, nous commençons à être capable de rédiger des programmes relativement complexes, même si vous n'en avez peut-être pas l'impression. Dans ces conditions, devoir réécrire le code entier de son programme à chaque fois qu'on ouvre l'interpréteur de commandes est assez lourd.
La solution ? Mettre notre code dans un fichier que nous pourrons lancer à volonté, comme un véritable programme !
Comme je l'ai dit dans le début de cette partie, il est grand temps que je vous montre cette possibilité. Mais on ne dit pas adieu à l'interpréteur de commandes pour autant. On lui dit juste au revoir pour cette fois... mais on le retrouvera bien assez tôt, la possibilité de tester notre code à la volée est vraiment un atout pour apprendre le langage.
Emprisonnons notre programme dans un fichier
Pour cette démonstration, je reprendrai le code optimisé du programme calculant si une année est bissextile. C'est un petit programme dont l'utilité est certes discutable mais il remplit un but précis, en l'occurrence dire si l'année entrée par l'utilisateur est bissextile ou non, et ça suffit pour un premier essai.
Je vous remet le code ici pour qu'on travaille tous sur les mêmes lignes, même si votre version marchera également sans problème dans un fichier, si elle tournait sous l'interpréteur de commandes.
Code : Python 1
2
3
4
5
6
7
8
9
10
11
# programme testant si une année, entrée par l'utilisateur,
# est bissextile ou non
print("Entrez une année :")
annee = input() # on attend que l'utilisateur entre l'année qu'il désire tester
annee = int(annee) # risque d'erreur si l'utilisateur n'a pas rentré un nombre
if annee%400==0 or (annee%4==0 and annee%100!=0):
print("L'année entrée est bissextile.")
else:
print("L'année entrée n'est pas bissextile.")
Ca va être à vous de travailler maintenant, je vais vous donner des pistes mais je ne vais pas me mettre à votre place, chacun prend ses habitudes en fonction de ses préférences
.
Ouvrez un éditeur basique, le bloc-notes Windows est candidat, Wordpad ou Word sont exclus. Sous Linux, vous pouvez utiliser vim ou emacs. Copiez et collez le code dans ce fichier. Enregistrez-le en précisant l'extension .py (exemple bissextile.py). Cela permettra au système d'exploitation de savoir qu'il doit utiliser Python pour exécuter ce programme (sous Windows, sous Linux ce n'est pas nécessaire).
Sous Linux, vous devrez rajouter dans votre fichier une ligne tout au début spécifiant le chemin de l'interpréteur Python (si vous avez déjà scripté en bash par exemple cette méthode ne vous surprendra pas). La première ligne de votre programme sera :
#!adresse
Remplacez adresse par l'adresse ou l'on peut trouver l'interpréteur, exemple : /usr/bin/python3. Vous devrez changer le droit d'exécution du fichier avant de l'exécuter comme un script.
Sous Windows, rendez-vous dans le dossier où vous avez enregistré votre fichier .py. Vous pouvez double-cliquer dessus, Windows saura qu'il doit appeler Python, grâce à l'extension .py, et Python reprend la main. Attendez toutefois car il reste quelques petites choses à régler avant de pouvoir exécuter votre programme.
Quelques ajustements
Quand on exécute un programme directement dans un fichier et que le programme contient des accents (et c'est le cas ici), il est nécessaire de préciser à Python l'encodage des accents. Je ne vais pas rentrer dans les détails, je vais simplement vous donner une ligne de code qu'il faudra mettre tout en haut de votre programme (sous Linux, juste en-dessous du chemin de l'interpréteur Python).
Code : Python1
# -*-coding:ENCODAGE -*
Sous Windows, vous devrez probablement remplacer "ENCODAGE" par "Latin-1". Sous Linux, ce sera plus vraissemblablement "Utf-8". Il n'est pas temps de faire un cours sur les encodages. Utilisez simplement la ligne qui marche chez vous sans oublier de la mettre et tout ira bien.
Il est probable, si vous exécutez votre application d'un double-clic, que votre programme se referme immédiatement après vous avoir demandé l'année. En fait, il fait bel et bien le calcul s'il n'y a pas eu d'erreur, mais il arrive à la fin du programme en une fraction de seconde et referme l'application, puisqu'elle est finie. Pour palier cette difficulté, il faut demander à votre programme de se mettre en pause à la fin de son exécution. Vous devrez rajouter une instruction un peu spéciale, un appel système qui marche sous Windows (pas sous Linux). Il faut tout d'abord importer le module os. Ensuite, on rajoute l'appel à la fonction os.system en lui passant en paramètre la chaîne de caractère "pause" (cela, à la fin de votre programme). Sous Linux, vous pouvez simplement exécuter votre programme dans la console ou, si vous tenez à faire une pause, utiliser par exemple input avant la fin de votre programme (pas bien élégant toutefois).
Voici donc, enfin, le code de votre premier programme l'encodage est à changer en fonction de votre système).
Code : Python 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# -*-coding:Latin-1 -*
import os # on importe le module os qui dispose de variables et de fonctions
# utiles pour dialoguer avec votre système d'exploitation
# programme testant si une année, entrée par l'utilisateur,
# est bissextile ou non
print("Entrez une année :")
annee = input() # on attend que l'utilisateur entre l'année qu'il désire tester
annee = int(annee) # risque d'erreur si l'utilisateur n'a pas rentré un nombre
# si l'année est bissextile ou non
if annee%400==0 or (annee%4==0 and annee%100!=0):
print("L'année entrée est bissextile.")
else:
print("L'année entrée n'est pas bissextile.")
# on met le programme en pause pour éviter qu'il ne se referme (Windows)
os.system("pause")
Quand vous exécutez ce script, que ce soit sous Windows ou Linux, vous faites toujours appel à l'interpréteur Python ! Votre programme n'est pas compilé, mais chaque ligne d'instruction est exécutée à la volée par l'interpréteur, le même que celui qui exécutait vos premiers programmes dans l'interpréteur de commandes. La grande différence ici est que Python exécute votre programme depuis le fichier et que donc, si vous souhaitez le modifier, il faudra modifier le fichier.
Sachez qu'il existe des éditeurs spécialisés pour Python, notamment Idle installé en même temps que Python, que personnellement je n'utilise pas. Vous pouvez l'ouvrir avec un clic droit sur votre fichier .py et regarder comment ça marche, ce n'est pas bien compliqué et vous avez la possibilité d'exécuter votre programme depuis ce logiciel. Mais étant donné que je ne l'utilise pas, je ne vous ferai pas un cours dessus. Si vous avez du mal à utiliser une des fonctionnalités du logiciel, recherchez sur Internet, d'autres tutoriels doivent exister, en anglais dans le pire des cas.
Je viens pour conquérir le monde... et créer mes propres modules
Mes modules à moi
Bon, nous avons vu le plus dur... ça va ?
Rassurez-vous, nous n'allons rien faire de compliqué dans cette dernière partie. Le plus dur est derrière nous.
Commencez par vous créer un espace de test pour les petits programmes Python que nous allons être amenés à faire, un joli dossier à l'écart de vos photos et musiques
. Nous allons créer deux fichiers .py dans ce dossier :
Vous devriez vous en tirer sans problème. N'oubliez pas de spécifier la ligne contenant l'encodage en tête de vos deux fichiers. Maintenant, voyons le code du fichier multipli.py.
Code : Python 1
2
3
4
5
6
7
8
9
10
"""module multipli contenant la fonction table"""
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
On se contente de définir une seule fonction, table, qui affiche la table de multiplication choisie. Rien de nouveau jusqu'ici. Si vous vous souvenez des docstrings, au chapitre précédent, nous en avons mis une nouvelle ici, non pas pour commenter une fonction mais bien un module entier. C'est une bonne habitude à prendre quand nos projets deviennent important.
Voici le code du fichier test.py, n'oubliez pas la ligne de votre encodage en haut
.
Code : Python1
2
3
4
5
6
import os
from multipli import *
# test de la fonction table
table(3, 20)
os.system("pause")
En le lançant directement voilà ce qu'on obtient :
Code : Console
1 * 3 = 3
2 * 3 = 6
3 * 3 = 9
4 * 3 = 12
5 * 3 = 15
6 * 3 = 18
7 * 3 = 21
8 * 3 = 24
9 * 3 = 27
10 * 3 = 30
11 * 3 = 33
12 * 3 = 36
13 * 3 = 39
14 * 3 = 42
15 * 3 = 45
16 * 3 = 48
17 * 3 = 51
18 * 3 = 54
19 * 3 = 57
20 * 3 = 60
Appuyez sur une touche pour continuer...
Je ne pense pas avoir grand chose à ajouter. Nous avons vu comment créer un module, il suffit de le mettre dans un fichier. On peut alors l'importer depuis un autre fichier contenu dans le même répertoire en précisant le nom du fichier (sans l'extension .py). Notre code encore une fois n'est pas très utile mais vous pouvez le modifier pour le rendre plus intéressant, vous en avez parfaitement les compétences à présent
.
Vous avez pu remarquer l'apparition du fichier multipli.pyc dans votre dossier de test. Ce fichier est généré par Python et contient le code compilé (ou presque) de votre module. Il ne s'agit pas réellement de langage machine, mais d'un format que Python décode un peu plus vite que le code que vous pouvez écrire. Python se charge lui-même de générer ce fichier et vous n'avez pas vraiment besoin de vous en soucier quand vous codez, ne soyez juste pas surpris.
Faire un test de module dans le module-même
Dans l'exemple que nous venons de voir, nous avons créé deux fichiers, le premier contenant un module, le second testant ledit module. Mais on peut très facilement tester le code d'un module dans le module-même. Cela veut dire que vous pourriez exécuter votre module comme un programme à lui tout seul, un programme qui testerait le module écrit dans le même fichier. Voyons voir cela
.
Reprenons le code du module "multipli" :
Code : Python 1
2
3
4
5
6
7
8
9
10
"""module multipli contenant la fonction table"""
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
Ce module définit une seule fonction, "table", qu'il pourrait être bon de tester. Oui mais... si nous rajoutons une ligne comme par exemple table(8) juste en-dessous, cette ligne sera exécutée lors de l'importation et donc, dans le programme appelant le module. Quand vous ferez import multipli , vous verrez la table de multiplication par 8 s'afficher... hum, il y a mieux
.
Heureusement, il y a un moyen très rapide de séparer le code qui sera exécuté si on lance le module directement en tant que programme, ou si on l'importe. Je vais vous livrer la solution que je détaillerai au-dessous :
Code : Python 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
"""module multipli contenant la fonction table"""
import os
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
# test de la fonction table
if __name__ == "__main__":
table(4)
os.system("pause")
N'oubliez pas la ligne indiquant l'encodage !
Voilà. A présent, si vous double-cliquez directement sur le fichier "multipli.py", vous allez voir la table de multiplication par 4. En revanche, si vous l'importez, le code de test ne s'exécutera pas. Tout repose en fait sur la variable __name__, c'est une variable qui existe dès le lancement de l'interpréteur. Si elle vaut "__main__", cela veut dire que le fichier appelé est le fichier exécuté. Autrement dit, si __name__ est égale à "__main__", vous pouvez mettre un code qui sera exécuté si le fichier est lancé directement comme un exécutable.
Prenez le temps de comprendre ce mécanisme, faites des tests si nécessaire, ça pourra vous être utile par la suite
.
Fini, l'interpréteur ?
Je le répète encore, l'interpréteur est véritablement très pratique pour un grand nombre de raisons. Et la meilleure d'entre elles est qu'il propose une manière interactive d'écrire un programme avec la possibilité de tester à chaque instruction le résultat. Toutefois, l'interpréteur a aussi un défaut : le code que vous entrez est effacé à la fermeture de la fenêtre. Or, nous commençons à être capable de rédiger des programmes relativement complexes, même si vous n'en avez peut-être pas l'impression. Dans ces conditions, devoir réécrire le code entier de son programme à chaque fois qu'on ouvre l'interpréteur de commandes est assez lourd.
La solution ? Mettre notre code dans un fichier que nous pourrons lancer à volonté, comme un véritable programme !
Comme je l'ai dit dans le début de cette partie, il est grand temps que je vous montre cette possibilité. Mais on ne dit pas adieu à l'interpréteur de commandes pour autant. On lui dit juste au revoir pour cette fois... mais on le retrouvera bien assez tôt, la possibilité de tester notre code à la volée est vraiment un atout pour apprendre le langage.
Emprisonnons notre programme dans un fichier
Pour cette démonstration, je reprendrai le code optimisé du programme calculant si une année est bissextile. C'est un petit programme dont l'utilité est certes discutable mais il remplit un but précis, en l'occurrence dire si l'année entrée par l'utilisateur est bissextile ou non, et ça suffit pour un premier essai.
Je vous remet le code ici pour qu'on travaille tous sur les mêmes lignes, même si votre version marchera également sans problème dans un fichier, si elle tournait sous l'interpréteur de commandes.
Code : Python 1
2
3
4
5
6
7
8
9
10
11
# programme testant si une année, entrée par l'utilisateur,
# est bissextile ou non
print("Entrez une année :")
annee = input() # on attend que l'utilisateur entre l'année qu'il désire tester
annee = int(annee) # risque d'erreur si l'utilisateur n'a pas rentré un nombre
if annee%400==0 or (annee%4==0 and annee%100!=0):
print("L'année entrée est bissextile.")
else:
print("L'année entrée n'est pas bissextile.")
Ca va être à vous de travailler maintenant, je vais vous donner des pistes mais je ne vais pas me mettre à votre place, chacun prend ses habitudes en fonction de ses préférences
Ouvrez un éditeur basique, le bloc-notes Windows est candidat, Wordpad ou Word sont exclus. Sous Linux, vous pouvez utiliser vim ou emacs. Copiez et collez le code dans ce fichier. Enregistrez-le en précisant l'extension .py (exemple bissextile.py). Cela permettra au système d'exploitation de savoir qu'il doit utiliser Python pour exécuter ce programme (sous Windows, sous Linux ce n'est pas nécessaire).
Sous Linux, vous devrez rajouter dans votre fichier une ligne tout au début spécifiant le chemin de l'interpréteur Python (si vous avez déjà scripté en bash par exemple cette méthode ne vous surprendra pas). La première ligne de votre programme sera :
#!adresse
Remplacez adresse par l'adresse ou l'on peut trouver l'interpréteur, exemple : /usr/bin/python3. Vous devrez changer le droit d'exécution du fichier avant de l'exécuter comme un script.
Sous Windows, rendez-vous dans le dossier où vous avez enregistré votre fichier .py. Vous pouvez double-cliquer dessus, Windows saura qu'il doit appeler Python, grâce à l'extension .py, et Python reprend la main. Attendez toutefois car il reste quelques petites choses à régler avant de pouvoir exécuter votre programme.
Quelques ajustements
Quand on exécute un programme directement dans un fichier et que le programme contient des accents (et c'est le cas ici), il est nécessaire de préciser à Python l'encodage des accents. Je ne vais pas rentrer dans les détails, je vais simplement vous donner une ligne de code qu'il faudra mettre tout en haut de votre programme (sous Linux, juste en-dessous du chemin de l'interpréteur Python).
Code : Python1
# -*-coding:ENCODAGE -*
Sous Windows, vous devrez probablement remplacer "ENCODAGE" par "Latin-1". Sous Linux, ce sera plus vraissemblablement "Utf-8". Il n'est pas temps de faire un cours sur les encodages. Utilisez simplement la ligne qui marche chez vous sans oublier de la mettre et tout ira bien.
Il est probable, si vous exécutez votre application d'un double-clic, que votre programme se referme immédiatement après vous avoir demandé l'année. En fait, il fait bel et bien le calcul s'il n'y a pas eu d'erreur, mais il arrive à la fin du programme en une fraction de seconde et referme l'application, puisqu'elle est finie. Pour palier cette difficulté, il faut demander à votre programme de se mettre en pause à la fin de son exécution. Vous devrez rajouter une instruction un peu spéciale, un appel système qui marche sous Windows (pas sous Linux). Il faut tout d'abord importer le module os. Ensuite, on rajoute l'appel à la fonction os.system en lui passant en paramètre la chaîne de caractère "pause" (cela, à la fin de votre programme). Sous Linux, vous pouvez simplement exécuter votre programme dans la console ou, si vous tenez à faire une pause, utiliser par exemple input avant la fin de votre programme (pas bien élégant toutefois).
Voici donc, enfin, le code de votre premier programme l'encodage est à changer en fonction de votre système).
Code : Python 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# -*-coding:Latin-1 -*
import os # on importe le module os qui dispose de variables et de fonctions
# utiles pour dialoguer avec votre système d'exploitation
# programme testant si une année, entrée par l'utilisateur,
# est bissextile ou non
print("Entrez une année :")
annee = input() # on attend que l'utilisateur entre l'année qu'il désire tester
annee = int(annee) # risque d'erreur si l'utilisateur n'a pas rentré un nombre
# si l'année est bissextile ou non
if annee%400==0 or (annee%4==0 and annee%100!=0):
print("L'année entrée est bissextile.")
else:
print("L'année entrée n'est pas bissextile.")
# on met le programme en pause pour éviter qu'il ne se referme (Windows)
os.system("pause")
Quand vous exécutez ce script, que ce soit sous Windows ou Linux, vous faites toujours appel à l'interpréteur Python ! Votre programme n'est pas compilé, mais chaque ligne d'instruction est exécutée à la volée par l'interpréteur, le même que celui qui exécutait vos premiers programmes dans l'interpréteur de commandes. La grande différence ici est que Python exécute votre programme depuis le fichier et que donc, si vous souhaitez le modifier, il faudra modifier le fichier.
Sachez qu'il existe des éditeurs spécialisés pour Python, notamment Idle installé en même temps que Python, que personnellement je n'utilise pas. Vous pouvez l'ouvrir avec un clic droit sur votre fichier .py et regarder comment ça marche, ce n'est pas bien compliqué et vous avez la possibilité d'exécuter votre programme depuis ce logiciel. Mais étant donné que je ne l'utilise pas, je ne vous ferai pas un cours dessus. Si vous avez du mal à utiliser une des fonctionnalités du logiciel, recherchez sur Internet, d'autres tutoriels doivent exister, en anglais dans le pire des cas.
Je viens pour conquérir le monde... et créer mes propres modules
Mes modules à moi
Bon, nous avons vu le plus dur... ça va ?
Commencez par vous créer un espace de test pour les petits programmes Python que nous allons être amenés à faire, un joli dossier à l'écart de vos photos et musiques
- Un fichier multipli.py qui contiendra notre fonction table que nous avons codé au début de ce chapitre
- Un fichier test.py qui contiendra le test d'exécution de notre module
Vous devriez vous en tirer sans problème. N'oubliez pas de spécifier la ligne contenant l'encodage en tête de vos deux fichiers. Maintenant, voyons le code du fichier multipli.py.
Code : Python 1
2
3
4
5
6
7
8
9
10
"""module multipli contenant la fonction table"""
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
On se contente de définir une seule fonction, table, qui affiche la table de multiplication choisie. Rien de nouveau jusqu'ici. Si vous vous souvenez des docstrings, au chapitre précédent, nous en avons mis une nouvelle ici, non pas pour commenter une fonction mais bien un module entier. C'est une bonne habitude à prendre quand nos projets deviennent important.
Voici le code du fichier test.py, n'oubliez pas la ligne de votre encodage en haut
Code : Python1
2
3
4
5
6
import os
from multipli import *
# test de la fonction table
table(3, 20)
os.system("pause")
En le lançant directement voilà ce qu'on obtient :
Code : Console
1 * 3 = 3
2 * 3 = 6
3 * 3 = 9
4 * 3 = 12
5 * 3 = 15
6 * 3 = 18
7 * 3 = 21
8 * 3 = 24
9 * 3 = 27
10 * 3 = 30
11 * 3 = 33
12 * 3 = 36
13 * 3 = 39
14 * 3 = 42
15 * 3 = 45
16 * 3 = 48
17 * 3 = 51
18 * 3 = 54
19 * 3 = 57
20 * 3 = 60
Appuyez sur une touche pour continuer...
Je ne pense pas avoir grand chose à ajouter. Nous avons vu comment créer un module, il suffit de le mettre dans un fichier. On peut alors l'importer depuis un autre fichier contenu dans le même répertoire en précisant le nom du fichier (sans l'extension .py). Notre code encore une fois n'est pas très utile mais vous pouvez le modifier pour le rendre plus intéressant, vous en avez parfaitement les compétences à présent
Vous avez pu remarquer l'apparition du fichier multipli.pyc dans votre dossier de test. Ce fichier est généré par Python et contient le code compilé (ou presque) de votre module. Il ne s'agit pas réellement de langage machine, mais d'un format que Python décode un peu plus vite que le code que vous pouvez écrire. Python se charge lui-même de générer ce fichier et vous n'avez pas vraiment besoin de vous en soucier quand vous codez, ne soyez juste pas surpris.
Faire un test de module dans le module-même
Dans l'exemple que nous venons de voir, nous avons créé deux fichiers, le premier contenant un module, le second testant ledit module. Mais on peut très facilement tester le code d'un module dans le module-même. Cela veut dire que vous pourriez exécuter votre module comme un programme à lui tout seul, un programme qui testerait le module écrit dans le même fichier. Voyons voir cela
Reprenons le code du module "multipli" :
Code : Python 1
2
3
4
5
6
7
8
9
10
"""module multipli contenant la fonction table"""
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
Ce module définit une seule fonction, "table", qu'il pourrait être bon de tester. Oui mais... si nous rajoutons une ligne comme par exemple table(8) juste en-dessous, cette ligne sera exécutée lors de l'importation et donc, dans le programme appelant le module. Quand vous ferez import multipli , vous verrez la table de multiplication par 8 s'afficher... hum, il y a mieux
Heureusement, il y a un moyen très rapide de séparer le code qui sera exécuté si on lance le module directement en tant que programme, ou si on l'importe. Je vais vous livrer la solution que je détaillerai au-dessous :
Code : Python 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
"""module multipli contenant la fonction table"""
import os
def table(nb, max=10):
"""Fonction affichant la table de multiplication par nb de
1 * nb jusqu'à max * nb
"""
i = 0
while i<max:
print(i+1 , "*" , nb , "=" , (i+1)*nb)
i += 1
# test de la fonction table
if __name__ == "__main__":
table(4)
os.system("pause")
N'oubliez pas la ligne indiquant l'encodage !
Voilà. A présent, si vous double-cliquez directement sur le fichier "multipli.py", vous allez voir la table de multiplication par 4. En revanche, si vous l'importez, le code de test ne s'exécutera pas. Tout repose en fait sur la variable __name__, c'est une variable qui existe dès le lancement de l'interpréteur. Si elle vaut "__main__", cela veut dire que le fichier appelé est le fichier exécuté. Autrement dit, si __name__ est égale à "__main__", vous pouvez mettre un code qui sera exécuté si le fichier est lancé directement comme un exécutable.
Prenez le temps de comprendre ce mécanisme, faites des tests si nécessaire, ça pourra vous être utile par la suite