python_icon

1) Les environnements virtuels python venv et virtualenv

Un des modules intégré à Python 3 est venv. Il permet de créer facilement et rapidement un environnement virtuel dans lequel on peut installer et exécuter des programmes Python.
Il imite une installation système complète de Python et de tous les modules souhaités sans interférer avec aucun système sur lequel l'application pourrait fonctionner.
Voyons comment créer un environnement virtuel et comment ajouter un module python.

pi@raspberrypi2:~/Documents $ pwd
/home/pi/Documents

# On cree un repertoire qui sera notre environnement virtuel
pi@raspberrypi2:~/Documents $ mkdir PM
pi@raspberrypi2:~/Documents $ ls -l
total 4
drwxr-xr-x 2 pi pi 4096 sept. 27 17:49 PM
pi@raspberrypi2:~/Documents $ python3 --version
Python 3.5.3

# On cree l'environnement virtuel
pi@raspberrypi2:~/Documents $ python3 -m venv /home/pi/Documents/PM

# On regarde simplement ce qui a ete cree
pi@raspberrypi2:~/Documents $ ls -l PM/
total 20
drwxr-xr-x 2 pi pi 4096 sept. 27 17:50 bin
drwxr-xr-x 2 pi pi 4096 sept. 27 17:50 include
drwxr-xr-x 3 pi pi 4096 sept. 27 17:50 lib
-rw-r--r-- 1 pi pi   69 sept. 27 17:50 pyvenv.cfg
drwxr-xr-x 3 pi pi 4096 sept. 27 17:50 share
pi@raspberrypi2:~/Documents $ ls -l PM/bin/
total 32
-rw-r--r-- 1 pi pi 2133 sept. 27 17:50 activate
-rw-r--r-- 1 pi pi 1249 sept. 27 17:50 activate.csh
-rw-r--r-- 1 pi pi 2413 sept. 27 17:50 activate.fish
-rwxr-xr-x 1 pi pi  251 sept. 27 17:50 easy_install
-rwxr-xr-x 1 pi pi  251 sept. 27 17:50 easy_install-3.5
-rwxr-xr-x 1 pi pi  223 sept. 27 17:50 pip
-rwxr-xr-x 1 pi pi  223 sept. 27 17:50 pip3
-rwxr-xr-x 1 pi pi  223 sept. 27 17:50 pip3.5
lrwxrwxrwx 1 pi pi    7 sept. 27 17:50 python -> python3
lrwxrwxrwx 1 pi pi   16 sept. 27 17:50 python3 -> /usr/bin/python3

# On active l'environnement
pi@raspberrypi2:~/Documents $ source /home/pi/Documents/PM/bin/activate

# On constate deja que le prompt a change
(PM) pi@raspberrypi2:~/Documents $

# On regarde les versions des outils installes
(PM) pi@raspberrypi2:~/Documents $ cd PM/
(PM) pi@raspberrypi2:~/Documents/PM $ which pip
/home/pi/Documents/PM/bin/pip
(PM) pi@raspberrypi2:~/Documents/PM $ pip --version
pip 9.0.1 from /home/pi/Documents/PM/lib/python3.5/site-packages (python 3.5)
(PM) pi@raspberrypi2:~/Documents/PM $ pip3 --version
pip 9.0.1 from /home/pi/Documents/PM/lib/python3.5/site-packages (python 3.5)

# On utilise pip pour installer un module python
(PM) pi@raspberrypi2:~/Documents/PM $ pip install snakeviz
Collecting snakeviz
  Downloading https://files.pythonhosted.org/packages/91/c1/79a997be084ea26d269244800db4be8c457816ca777b4b134c72514079b3/snakeviz-2.0.1-py2.py3-none-any.whl (281kB)
    100% |████████████████████████████████| 286kB 507kB/s 
Collecting tornado>=2.0 (from snakeviz)
  Downloading https://www.piwheels.org/simple/tornado/tornado-6.0.3-cp35-cp35m-linux_armv7l.whl (425kB)
    100% |████████████████████████████████| 430kB 176kB/s 
Installing collected packages: tornado, snakeviz
Successfully installed snakeviz-2.0.1 tornado-6.0.3

# On liste les modules python installes
(PM) pi@raspberrypi2:~/Documents/PM $ pip list
DEPRECATION: The default format will switch to columns in the future. You can use --format=(legacy|columns) (or define a format=(legacy|columns) in your pip.conf under the [list] section) to disable this warning.
pip (9.0.1)
pkg-resources (0.0.0)
setuptools (33.1.1)
snakeviz (2.0.1)
tornado (6.0.3)

# On quitte (exit) l'environnement virtuel
(PM) pi@raspberrypi2:~/Documents/PM $ deactivate
pi@raspberrypi2:~/Documents/PM $


Il est aussi possible de créer un environnement virtuel avec Python 2:

pi@raspberrypi2:~/Documents $ python --version
Python 2.7.13
pi@raspberrypi2:~/Documents $ which python
/usr/bin/python

# On crée le répertoire qui contiendra l'environnement virtuel
pi@raspberrypi2:~/Documents $ mkdir PM

# S'il n'existe pas, on installe virtualenv
pi@raspberrypi2:~/Documents $ pip install virtualenv
Collecting virtualenv
  Downloading https://files.pythonhosted.org/packages/62/77/6a86ef945ad39aae34aed4cc1ae4a2f941b9870917a974ed7c5b6f137188/virtualenv-16.7.8-py2.py3-none-any.whl (3.4MB)
    100% |████████████████████████████████| 3.4MB 48kB/s 
Installing collected packages: virtualenv
Successfully installed virtualenv-16.7.8

# On crée l'environnement virtuel
pi@raspberrypi2:~/Documents $ python -m virtualenv /home/pi/Documents/PM
New python executable in /home/pi/Documents/PM/bin/python
Installing setuptools, pip, wheel...
done.
pi@raspberrypi2:~/Documents $ ls -ltr PM
total 16
drwxr-xr-x 3 pi pi 4096 déc.  15 17:42 lib
drwxr-xr-x 2 pi pi 4096 déc.  15 17:42 include
drwxr-xr-x 2 pi pi 4096 déc.  15 17:42 local
drwxr-xr-x 2 pi pi 4096 déc.  15 17:42 bin
pi@raspberrypi2:~/Documents $

# On se place dans l'environnement virtuel (activation)
pi@raspberrypi2:~/Documents $ cd PM
pi@raspberrypi2:~/Documents/PM $ source bin/activate
(PM) pi@raspberrypi2:~/Documents/PM $


2) Un premier script pour débuter en python

Voici un petit script en python3 qui permet de déterminer si un nombre est premier ou non. L'image ci-dessous montre également quelques exécutions sur Kubuntu 19.04:

prabou@prabou-VPCZ23C5E:~/Téléchargements$ cat is_prime.py
#!/usr/bin/env python3
#File: is_prime.py
#Author: Prabou MOUTTOU
#Description: checks if nombre is prime
#Version: 29 April 2019

import sys, math

nombre = int(sys.argv[1])
if (nombre%2 == 0):
        print(nombre,"est pair, il n'est donc pas premier")
else:
        #calcul de la partie entiere de la racine carree du nombre
        partie_entiere = int(math.sqrt(nombre))
        if (partie_entiere%2 == 0):
                partie_entiere = partie_entiere - 1

        #calcul du reste de l'operation nombre/3,5,7...$partie_entiere
        i = 3
        while ((nombre%i != 0) & (i <= partie_entiere)) :  
                i = i+2

        if ((i-2) != partie_entiere):
           print(nombre,"n'est pas premier!", nombre,"est divisible par", i)
        else:
           print(nombre,"est premier!")
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./is_prime.py 37
37 est premier!
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./is_prime.py 39
39 n'est pas premier! 39 est divisible par 3
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./is_prime.py 391
391 n'est pas premier! 391 est divisible par 17
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./is_prime.py 396
396 est pair, il n'est donc pas premier
prabou@prabou-VPCZ23C5E:~/Téléchargements$


3) Un deuxième script

Un script python qui répond au Problème 1 (Multiples of 3 and 5) du Project Euler.

L'image ci-dessous montre le problème, suivi de quelques exécutions du script:


prabou@prabou-VPCZ23C5E:~/Téléchargements$ cat projecteuler_pb1.py
#!/usr/bin/python
#File: projecteuler_pb1.py
#Author: Prabou MOUTTOU
#Description: find the sum of all the multiples of 3 or 5 below 1000 (https://projecteuler.net/archives)
#Version: 20 december 2015

import sys, math

nombre = int(sys.argv[1])
sum = 0
for i in range(1,nombre):
 if (i%3 == 0) or (i%5 == 0):   # si i est multiple de 3 ou de 5 on actualise sum
  sum = sum + i

print "la somme vaut %d" %sum
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./projecteuler_pb1.py 10
la somme vaut 23
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ./projecteuler_pb1.py 1000
la somme vaut 233168
prabou@prabou-VPCZ23C5E:~/Téléchargements$


4) Pylint, Pycodestyle et Black

Un script python qui répond au Problème 10 (Summation of primes) du Project Euler.
L'image ci-dessous montre le problème, suivi de l'exécution du script, et enfin l'amélioration de la qualité du code avec pylint, pycodestyle et black:


prabou@prabou-VPCZ23C5E:~/Documents/DEV$ cat projecteuler_pb10.py
#!/usr/bin/env python3
"""File: projecteuler_pb10.py
Author: Prabou MOUTTOU
Description: resolution of projecteuler_pb10
Version: 15 May 2020"""

import sys
import math

MYNUMBER = int(sys.argv[1])

def isprime(nombre):
    """Checks if nombre is prime"""
    # If nombre is Even, then it is not prime
    if nombre%2 == 0:
        return False
    else:
        # calcul de la partie entiere de la racine carree du nombre
        partie_entiere = int(math.sqrt(nombre))
        if partie_entiere%2 == 0:
            partie_entiere = partie_entiere - 1

        # calcul du reste de l'operation nombre/3,5,7...$partie_entiere
        i = 3
        while (nombre%i != 0) & (i <= partie_entiere):
            i = i+2

        if (i-2) != partie_entiere:
            return False
        return True

def main():
    """If j is prime then add total = total + j"""
    total = 2
    for j in range(3, MYNUMBER+1):
        if isprime(j):
            total = total+j
    print("TOTAL=", total)

if __name__ == '__main__':
    main()
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ ./projecteuler_pb10.py 10
TOTAL= 17
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ ./projecteuler_pb10.py 2000000
TOTAL= 142913828922

# pylint installation
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ sudo apt install pylint

# Code analysis
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ pylint projecteuler_pb10.py
************* Module projecteuler_pb10
projecteuler_pb10.py:15:4: R1705: Unnecessary "else" after "return" (no-else-return)

------------------------------------------------------------------
Your code has been rated at 9.57/10 (previous run: 9.57/10, +0.00)

# pycodestyle installation
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ pip3 install pycodestyle
Collecting pycodestyle
  Downloading pycodestyle-2.6.0-py2.py3-none-any.whl (41 kB)
     |████████████████████████████████| 41 kB 115 kB/s 
Installing collected packages: pycodestyle
Successfully installed pycodestyle-2.6.0

# style conventions check with pycodestyle
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ pycodestyle projecteuler_pb10.py
projecteuler_pb10.py:12:1: E302 expected 2 blank lines, found 1
projecteuler_pb10.py:15:14: E228 missing whitespace around modulo operator
projecteuler_pb10.py:20:26: E228 missing whitespace around modulo operator
projecteuler_pb10.py:25:22: E228 missing whitespace around modulo operator
projecteuler_pb10.py:32:1: E302 expected 2 blank lines, found 1
projecteuler_pb10.py:40:1: E305 expected 2 blank lines after class or function definition, found 1

# black installation
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ pip3 install black
Collecting black
  Downloading black-20.8b1.tar.gz (1.1 MB)
     |████████████████████████████████| 1.1 MB 234 kB/s 
  Installing build dependencies ... done
  Getting requirements to build wheel ... done
    Preparing wheel metadata ... done
Collecting typed-ast>=1.4.0
  Downloading typed_ast-1.4.2-cp38-cp38-manylinux1_x86_64.whl (774 kB)
     |████████████████████████████████| 774 kB 26 kB/s 
Collecting click>=7.1.2
  Downloading click-7.1.2-py2.py3-none-any.whl (82 kB)
     |████████████████████████████████| 82 kB 189 kB/s 
Collecting mypy-extensions>=0.4.3
  Downloading mypy_extensions-0.4.3-py2.py3-none-any.whl (4.5 kB)
Collecting regex>=2020.1.8
  Downloading regex-2021.4.4-cp38-cp38-manylinux2014_x86_64.whl (733 kB)
     |████████████████████████████████| 733 kB 117 kB/s 
Collecting pathspec<1,>=0.6
  Downloading pathspec-0.8.1-py2.py3-none-any.whl (28 kB)
Collecting typing-extensions>=3.7.4
  Downloading typing_extensions-3.7.4.3-py3-none-any.whl (22 kB)
Collecting appdirs
  Downloading appdirs-1.4.4-py2.py3-none-any.whl (9.6 kB)
Collecting toml>=0.10.1
  Downloading toml-0.10.2-py2.py3-none-any.whl (16 kB)
Building wheels for collected packages: black
  Building wheel for black (PEP 517) ... done
  Created wheel for black: filename=black-20.8b1-py3-none-any.whl size=124184 sha256=0e66ef978971465b51b933354196cf311524ec6c287a5e84de87714b2a954f50
  Stored in directory: /home/prabou/.cache/pip/wheels/95/a4/59/10cd5378d52f92cdb45025f040e4686e10ae5217961c25fd66
Successfully built black
Installing collected packages: typed-ast, click, mypy-extensions, regex, pathspec, typing-extensions, appdirs, toml, black
Successfully installed appdirs-1.4.4 black-20.8b1 click-7.1.2 mypy-extensions-0.4.3 pathspec-0.8.1 regex-2021.4.4 toml-0.10.2 typed-ast-1.4.2 typing-extensions-3.7.4.3

# python code formatter
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ black projecteuler_pb10.py
reformatted projecteuler_pb10.py
All done! ✨ 🍰 ✨
1 file reformatted.
prabou@prabou-VPCZ23C5E:~/Documents/DEV$

Si vous souhaitez aller plus loin et faire du "Profiling", on peut installer Snakeviz.

Remarque: Le profiling est utilisé pour mesurer le temps que passe un programme dans chaque fonction.

# On installe pip3 (càd pip pour Python3)
prabou@prabou-VPCZ23C5E:~/Téléchargements$ sudo apt install python3-pip

# On installe Snakeviz
prabou@prabou-VPCZ23C5E:~/Téléchargements$ pip3 install snakeviz

# Lister les packages avec pip3
prabou@prabou-VPCZ23C5E:~/Téléchargements$ pip3 list
Package                Version    
---------------------- -----------
apt-xapian-index       0.47       
asn1crypto             0.24.0     
certifi                2018.8.24  
chardet                3.0.4      
command-not-found      0.3        
cryptography           2.3        
cson                   0.7        
cupshelpers            1.0        
defer                  1.0.6      
distro-info            0.21ubuntu2
entrypoints            0.3        
httplib2               0.11.3     
idna                   2.6        
keyring                17.1.1     
keyrings.alt           3.1.1      
language-selector      0.1        
netifaces              0.10.4     
numpy                  1.16.2     
olefile                0.46       
pexpect                4.6.0      
Pillow                 5.4.1      
pip                    18.1       
pycairo                1.16.2     
pycrypto               2.6.1      
pycups                 1.9.73     
PyGObject              3.32.0     
pymacaroons            0.13.0     
PyNaCl                 1.3.0      
PyQt5                  5.12.1     
python-apt             1.8.4      
python-debian          0.1.34     
pyxdg                  0.25       
PyYAML                 3.13       
reportlab              3.5.18     
requests               2.21.0     
requests-unixsocket    0.1.5      
SecretStorage          2.3.1      
setuptools             40.8.0     
six                    1.12.0     
snakeviz               2.0.0      
speg                   0.3        
systemd-python         234        
tornado                6.0.2      
ubuntu-advantage-tools 19.2       
ubuntu-drivers-common  0.0.0      
ufw                    0.36       
unattended-upgrades    0.1        
urllib3                1.24.1     
wheel                  0.32.3     
xkit                   0.0.0      
prabou@prabou-VPCZ23C5E:~$

# On peut directement lancer le profilage avec le module cProfile
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ python3 -m cProfile -s time projecteuler_pb10.py 2000000
TOTAL= 142913828922
         3000056 function calls in 9.625 seconds

   Ordered by: internal time

   ncalls  tottime  percall  cumtime  percall filename:lineno(function)
  1999998    9.187    0.000    9.307    0.000 projecteuler_pb10.py:12(isprime)
        1    0.317    0.317    9.625    9.625 projecteuler_pb10.py:32(main)
   999999    0.121    0.000    0.121    0.000 {built-in method math.sqrt}
        1    0.000    0.000    0.000    0.000 {built-in method builtins.print}
        1    0.000    0.000    0.000    0.000 {built-in method _imp.create_builtin}
        1    0.000    0.000    0.000    0.000 :986(_find_and_load)
        1    0.000    0.000    9.625    9.625 projecteuler_pb10.py:2()
        1    0.000    0.000    0.000    0.000 :157(_get_module_lock)
        1    0.000    0.000    0.000    0.000 :650(_load_unlocked)
        1    0.000    0.000    0.000    0.000 :406(spec_from_loader)
        1    0.000    0.000    0.000    0.000 :477(_init_module_attrs)
        1    0.000    0.000    0.000    0.000 :890(_find_spec)
        1    0.000    0.000    0.000    0.000 :78(acquire)
        1    0.000    0.000    0.000    0.000 :956(_find_and_load_unlocked)
        2    0.000    0.000    0.000    0.000 :211(_call_with_frames_removed)
        1    0.000    0.000    0.000    0.000 :103(release)
        4    0.000    0.000    0.000    0.000 {built-in method builtins.getattr}
        1    0.000    0.000    0.000    0.000 :58(__init__)
        1    0.000    0.000    0.000    0.000 :725(find_spec)
        1    0.000    0.000    0.000    0.000 :549(module_from_spec)
        1    0.000    0.000    9.625    9.625 {built-in method builtins.exec}
        1    0.000    0.000    0.000    0.000 :746(create_module)
        4    0.000    0.000    0.000    0.000 {built-in method builtins.hasattr}
        1    0.000    0.000    0.000    0.000 :232(_requires_builtin_wrapper)
        1    0.000    0.000    0.000    0.000 :176(cb)
        1    0.000    0.000    0.000    0.000 :147(__enter__)
        1    0.000    0.000    0.000    0.000 :389(parent)
        1    0.000    0.000    0.000    0.000 :754(exec_module)
        1    0.000    0.000    0.000    0.000 :342(__init__)
        1    0.000    0.000    0.000    0.000 :867(__exit__)
        1    0.000    0.000    0.000    0.000 {method 'disable' of '_lsprof.Profiler' objects}
        1    0.000    0.000    0.000    0.000 :151(__exit__)
        1    0.000    0.000    0.000    0.000 :143(__init__)
        1    0.000    0.000    0.000    0.000 :863(__enter__)
        3    0.000    0.000    0.000    0.000 {built-in method _imp.acquire_lock}
        3    0.000    0.000    0.000    0.000 {built-in method _imp.release_lock}
        2    0.000    0.000    0.000    0.000 {method 'get' of 'dict' objects}
        1    0.000    0.000    0.000    0.000 :222(_verbose_message)
        2    0.000    0.000    0.000    0.000 {built-in method _thread.get_ident}
        2    0.000    0.000    0.000    0.000 {method 'rpartition' of 'str' objects}
        2    0.000    0.000    0.000    0.000 {built-in method _thread.allocate_lock}
        1    0.000    0.000    0.000    0.000 {built-in method _imp.is_builtin}
        1    0.000    0.000    0.000    0.000 {built-in method _imp.exec_builtin}
        1    0.000    0.000    0.000    0.000 {method 'pop' of 'dict' objects}
        1    0.000    0.000    0.000    0.000 :397(has_location)
        1    0.000    0.000    0.000    0.000 :771(is_package)


prabou@prabou-VPCZ23C5E:~/Documents/DEV$

# On peut aussi générer un fichier profile (*.prof)
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ python3 -m cProfile -o projecteuler_pb10.prof projecteuler_pb10.py 2000000
TOTAL= 142913828922
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ ls -lrt | grep -i ".prof"
-rw-rw-r-- 1 prabou prabou   5244 mai   21 17:37 projecteuler_pb10.prof
prabou@prabou-VPCZ23C5E:~/Documents/DEV$

# Maintenant qu'on a le fichier projecteuler_pb10.prof, il faut l'ouvrir.

# Pour trouver le path où est installé snakeviz, on utilise les commandes suivantes:
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ pip3 show snakeviz
Name: snakeviz
Version: 2.1.0
Summary: A web-based viewer for Python profiler output
Home-page: https://github.com/jiffyclub/snakeviz
Author: Matt Davis
Author-email: jiffyclub@gmail.com
License: UNKNOWN
Location: /usr/local/lib/python3.8/dist-packages
Requires: tornado
Required-by: 
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ ls -ltr /usr/local/lib/python3.8/dist-packages
total 16
drwxr-sr-x 5 root staff 4096 mai   21 17:15 tornado
drwxr-sr-x 2 root staff 4096 mai   21 17:15 tornado-6.0.4.dist-info
drwxr-sr-x 2 root staff 4096 mai   21 17:15 snakeviz-2.1.0.dist-info
drwxr-sr-x 5 root staff 4096 mai   21 17:15 snakeviz
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ which snakeviz
/usr/local/bin/snakeviz
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ /usr/local/bin/snakeviz projecteuler_pb10.prof
snakeviz web server started on 127.0.0.1:8080; enter Ctrl-C to exit
http://127.0.0.1:8080/snakeviz/%2Fhome%2Fprabou%2FDocuments%2FDEV%2Fprojecteuler_pb10.prof

# Une autre méthode plus simple est d'utiliser la commande:
prabou@prabou-VPCZ23C5E:~/Documents/DEV$ python3 -m snakeviz projecteuler_pb10.prof
La dernière commande ci-dessus ouvrira Firefox avec un résultat qui ressemblera à ceci:

Si vous souhaitez faire en plus de la couverture de code, on peut installer Coverage:

# Installation de Coverage
prabou@prabou-VPCZ23C5E:~/Téléchargements$ pip3 install coverage
Collecting coverage
  Downloading https://files.pythonhosted.org/packages/b4/6a/8e2918c56682739cf177a7358929fed427d3982cc649e859b7a2d5c7daea/coverage-4.5.3-cp37-cp37m-manylinux1_x86_64.whl (204kB)
    100% |████████████████████████████████| 215kB 1.6MB/s 
Installing collected packages: coverage
Successfully installed coverage-4.5.3
# Mesure/test de couverture du code, il génère un fichier .coverage
prabou@prabou-VPCZ23C5E:~/Téléchargements$ coverage run projecteuler_pb10.py 2000
TOTAL= 277050
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ls -lart | grep -i "coverage"
-rw-rw-r--  1 prabou prabou      198 mai   22 21:18 .coverage
# La commande "coverage erase" permet de supprimer le fichier .coverage (càd supprimer le résultat de la dernière analyse)
prabou@prabou-VPCZ23C5E:~/Téléchargements$ coverage erase
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ls -lart | grep -i "coverage"
prabou@prabou-VPCZ23C5E:~/Téléchargements$
# Comme on vient de supprimer la dernière mesure, on recommence le test
prabou@prabou-VPCZ23C5E:~/Téléchargements$ coverage run projecteuler_pb10.py 7
TOTAL= 17
prabou@prabou-VPCZ23C5E:~/Téléchargements$
# On choisit d'afficher le résultat directement dans le terminal
prabou@prabou-VPCZ23C5E:~/Téléchargements$ coverage report -m
Name                   Stmts   Miss  Cover   Missing
----------------------------------------------------
projecteuler_pb10.py      21      2    90%   27, 30
prabou@prabou-VPCZ23C5E:~/Téléchargements$
# On choisit de générer un beau rapport html (création du répertoire htmlcov)
prabou@prabou-VPCZ23C5E:~/Téléchargements$ coverage html
prabou@prabou-VPCZ23C5E:~/Téléchargements$ ls -lart | grep -i "cov"
-rw-rw-r--  1 prabou prabou      192 mai   22 21:34 .coverage
drwxrwxr-x  2 prabou prabou     4096 mai   22 21:35 htmlcov
prabou@prabou-VPCZ23C5E:~/Téléchargements$

Dans ce répertoire htmlcov, on retrouve notamment un fichier index.html qui ressemble à ceci:

coverage global report

, et un fichier projecteuler_pb10_py.html qui peut être affiché depuis index.html en cliquant sur le nom du fichier; et qui ressemble à ceci (affichage du code):


5) gspread

gspread est une API python pour Google Sheets. Elle permet d'automatiser la création/suppression d'une feuille de calcul dans un dossier spécifique de Google Drive.
Grâce à cette API, on peut lire le contenu d'une feuille, y écrire, et mettre en forme les données.

La vidéo suivante montre les différentes étapes de configuration, ainsi qu'un exemple d'utilisation.


6) Quelques modules python

Voici les modules matplotlib et numpy. Matplotlib permet de tracer et visualiser des données sous formes de graphiques.
Ci-dessous la fonction 1 + sin(2πt), pour t ∈ [0; 2]

import matplotlib.pyplot as plt
import numpy as np

t = np.arange(0.0, 2.0, 0.01)
s = 1 + np.sin(2*np.pi*t)
plt.plot(t, s)

plt.xlabel('time (s)')
plt.ylabel('voltage (mV)')
plt.title('About as simple as it gets, folks')
plt.grid(True)
plt.savefig("matplot_1.png")
plt.show()
Voici le résultat obtenu:

Ci-dessous une courbe obtenue simplement à partir de 4 points:

import matplotlib.pyplot as plt
plt.plot([1, 2, 3, 4], [1, 4, 9, 16])
plt.ylabel('some numbers')
plt.grid(True)
plt.show()

Ou si on souhaite afficher uniquement des points:

import matplotlib.pyplot as plt
import numpy as np

# evenly sampled time at 200ms intervals
t = np.arange(0., 5., 0.2)

# red dashes, blue squares, green triangles, fuchsia diamond...
plt.plot(t, t, 'r--')
plt.plot(t, t**2, 'bs')
plt.plot(t, t**3, 'g^')
plt.plot(t, t**4, color = '#FF00FF', linestyle = '', marker = 'D')
plt.plot(t, 80*t, color = '#FFA500', linestyle = 'dotted', marker = 'x')
plt.plot(t, 20*t, 'yo')
plt.plot(t, 3*np.exp(t), 'k*')
plt.show()