Dans ce tutoriel, nous allons apprendre à sauvegarder des tableaux numpy pour ajouter de la persistance à votre application python.
Notre première persistance
Sauvegarde des données
Pour sauvegarder votre tableau NumPy, on utilise le comportement natif de python pour l’ouverture d’un fichier, et on appelle la fonction save de NumPy :
import numpy as np
array = np.array([6, 9])
with open('array.npy', 'wb') as f:
np.save(f, array)
Le fichier en sortie utilise un format binaire spécifique numpy. Sur la première ligne, on trouve les paramètres de notre tableau persisté :
�NUMPYv{'descr': '<i8', 'fortran_order': False, 'shape': (2,), }
La suite du fichier est composée d’octets correspondant aux valeurs du tableau.
Chargement des données
Après avoir sauvegardé nos données, il faut pouvoir les charger. Pour cela, on
utilise la fonction load de numpy :
with open('array.npy', 'rb') as f:
array2 = np.load(f)
print(array2)
Ce qui donne le résultat suivant :
[6 9]
Et voilà, on a notre première persistance de données avec numpy !
Persistance au format texte
Il arrive qu’on veuille utiliser des données traitées avec numpy dans un autre langage de programmation, ou par exemple sur excel. On doit donc enregistrer nos données dans un format compréhensible par tous.
Sauvegarde des données
On utilise une autre fonction de numpy savetxt :
array = np.array([[6, 9, 42], [4, 2, 9]])
np.savetxt('array_float.csv', array, delimiter=',')
Le delimiter est le caractère au sein du fichier qui séparera nos valeurs. Les
délimiteurs courants sont , et ;.
Notre fichier csv contient :
6.000000000000000000e+00,9.000000000000000000e+00,4.200000000000000000e+01
4.000000000000000000e+00,2.000000000000000000e+00,9.000000000000000000e+00
Les nombres sont enregistrés par défaut en nombre flottant, pour régler ça, on spécifie un format à notre export :
np.savetxt('array_int.csv', array, delimiter=',', fmt='%i')
Finalement, on obtient un format en entier :
6,9,42
4,2,9
Chargement des données
Maintenant pour charger nos données enregistrées en format texte, on utilise loadtxt :
array_loaded_from_text = np.loadtxt('array_int.csv', delimiter=',')
print(array_loaded_from_text)
[[ 6. 9. 42.]
[ 4. 2. 9.]]
Compression en archive gz
Si la quantité de données est conséquente, il peut être intéressant de
compresser les données enregistrées. La fonction de sauvegarde utilisée
précédemment savetxt permet de compresser nativement les données, si le
fichier de sortie possède l’extension .gz (pour gzip ou GNU zip).
big_array = np.random.rand(1000, 1000) # tableau de 1000x1000
np.savetxt('array_test.csv', big_array, delimiter=',')
np.savetxt('array_compressed.gz', big_array, delimiter=',')
| Fichier | Taille |
|---|---|
| .csv | ~25,0 Mo |
| .gz | ~10,6 Mo |
Le gain de place est intéressant (le fichier compressé est plus de deux fois plus petit), cependant l’enregistrement et le chargement des données sauvegardées au format gz seront plus longs. Notez que sur des données aléatoires comme ici, la compression est loin d’être optimale : sur des données réelles, souvent plus régulières, le gain est généralement meilleur.
Le chargement se fait de la même façon que précédemment, la fonction loadtxt
se charge de décompresser pour nous les données.
big_array_loaded = np.loadtxt('array_compressed.gz', delimiter=',')
Persistance au format npz
NumPy propose une dernière façon de persister vos données avec le format npz, qui a l’avantage de pouvoir sauvegarder plusieurs tableaux numpy dans le même fichier et contrairement au format texte, ce format supporte des tableaux à n dimensions.
np.savez('test.npz', array=array, big_array=big_array)
loaded_npz = np.load('test.npz')
array_loaded_from_npz = loaded_npz['array']
big_array_loaded_from_npz = loaded_npz['big_array']
print(loaded_npz.files)
print(big_array_loaded_from_npz.shape)
Ce qui donne :
['array', 'big_array']
(1000, 1000)
De plus, NumPy propose avec le format npz de compresser facilement les
données :
np.savez_compressed('test_compressed.npz', array=array, big_array=big_array)
loaded_npz = np.load('test_compressed.npz')
array_loaded_from_npz = loaded_npz['array']
big_array_loaded_from_npz = loaded_npz['big_array']
Comme pour loadtxt la fonction load se charge de décompresser
automatiquement.
Conclusion
Voilà, vous êtes maintenant capable de faire persister vos données numpy.