FAQ PythonConsultez toutes les FAQ

Nombre d'auteurs : 15, nombre de questions : 269, dernière mise à jour : 10 septembre 2014  Ajouter une question

 

Cette FAQ a été réalisée à partir des questions posées sur le forum Python complétées par d'autres questions qui pouvaient nous sembler intéressantes de traiter. Toutefois il se peut que les réponses apportées contiennent des erreurs, imprécisions ... Vous pouvez dans ce cas contacter un des membres de la rédaction pour lui faire part de vos remarques.

L'équipe Python de Developpez.


SommaireProgrammation objet (5)
précédent sommaire suivant
 

Vous pouvez sauvegarder de manière très simples dans des fichiers des objets python basiques ou même des objets que vous auriez vous-mêmes définis.
S'il s'agit de nombres (int, float, ...), chaînes de caractères, conteneurs (tuples, listes, dictionnaires) contenant uniquement des objets de types élémentaires, vous pouvez utiliser le module marshal. Sinon, s'il s'agit d'instances de classe que vous avez vous-mêmes définis, utilisez le module pickle ou cPickle (qui est beaucoup plus rapide que pickle)

La fonction dump(value, file)value est l'objet élémentaire à sauvegarder et file est un fichier ouvert en écriture.
La focntion load(fileobj) permet de lire un fichier et retourne l'objet enregistré; fileobj étant un fichier ouvert en lecture.

Code python :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
import marshal 
import cPickle 
  
dico = {} 
dico['toto'] = [23,'53453',{'a':5}] 
marshal.dump(dico, open("mondico", 'wb')) ## Sauvegarde du dictionnaire  
print marshal.load(open("mondico", "rb")) ## Rechargement du dictionnaire 
  
class toto: 
    def __init__(self): 
        self.x = 5 
tutu = toto() 
cPickle.dump(tutu, open("toto2", "wb"))  ## Sauvegarde de l'objet tutu 
print cPickle.load(open("toto2")).x      ## Rechargement de l'objet tutu

Mis à jour le 13 avril 2006 Guigui_

Vous pouvez avoir besoin de travailler sur des objets contenant directement le contenu d'images ou bien de transférer des objets devant travailler sur des images. Vous devez tout d'abord récupérer et installer la bibliothèque Pil . Au lieu de devoir ainsi fournir un fichier contenant l'objet et chacune des images dans des fichier séparés ou dans un fichier .zip, vous pouvez alors décider d'utiliser un unique fichier qui peut ainsi faciliter la procédure. En revanche, si vous travaillez avec des images compressées, le fichier que nous allons créer sera beaucoup plus gros que l'ensemble des fichiers images le constituant.
Pour cela, il suffit tout d'abord d'ouvrir chaque image en tant fichier binaire grâce à la commande open et le paramètre 'rb' et de les conserver dans une variable ou un autre conteneur (comme une liste ou un dictionnaire).
la méthode seek(0) vous permet de vous placer au début du fichier et la méthode read() de lire le contenu entier du fichier ouvert.

Code python :
1
2
3
4
5
6
7
8
9
10
11
import cPickle 
img1 = open('first.jpg', 'rb') 
img1.seek(0) 
w1 = img1.read() 
img1.close() 
img2 = open('second.jpg', 'rb') 
img2.seek(0) 
w2 = img2.read() 
img2.close() 
dic = {'img1' : w1, 'img2': w2} 
cPickle.dump(dic, open("monfichier", "wb"))
Une fois que vous avez récupérer le fichier créé avec cPickle, vous pouvez récupérer en connaissant la structure du fichier les 2 images transmises. Pour cela, on va utiliser le module cStringIO qui permet de lire et de créer des fichiers en mémoire. Par la méthode write, nous allons écrire le contenu de nos variables, se repositionner avec seek(0) au début du fichier. Enfin, nous allon récréer une image grâce à Pil et la fonction Image.open.

Code python :
1
2
3
4
5
6
7
8
9
10
11
12
import Image, cPickle, cStringIO 
monobjet = cPickle.load(open("monfichier")) 
img1 = cStringIO.StringIO() 
img1.write(monobjet['img1']) 
img1.seek(0) 
im1 = Image.open(img1) 
im1.save('first.jpg') 
img2 = cStringIO.StringIO() 
img2.write(monobjet['img2']) 
img2.seek(0) 
im2 = Image.open(img2) 
im2.save('second.jpg')

Mis à jour le 23 octobre 2006 Guigui_

Vous pouvez récupérer le nom de la classe d'un objet en appliquant à cet objet l'attribut .__class__.__name__

Code python :
1
2
3
4
5
6
7
8
>>> a = 5 
>>> a.__class__.__name__ 
'int' 
>>> class toto: pass 
  
>>> b = toto() 
>>> b.__class__.__name__ 
'toto'

Mis à jour le 13 avril 2006 Guigui_

Les objets immuables que l'on utilise traditionnellement sont les nombres et les chaînes de caractères. Pour ces objets, on ne peut effectuer un héritage traditionnelle qui utilise la méthode __init__ qui n'a aucune influence sur la valeur retournée par le constructeur dans ce cas-là. Vous devez alors utiliser la méthode __new__(...) comme sur l'exemple suivant. Si vous redéfinissez ensuite des fonctions que la classe parente possède déjà, n'oubliez pas d'utiliser si nécessaire la fonction super(cls, obj) qui permet d'appeler les fonctions de la classe mère sous peine parfois d'obtenir des erreurs de récursion infinie. Etudiez ainsi l'exemple suivant où la classe angle dérive de la classe int en redéfinissant quelques fonctions basiques.

Code python :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class angle(int): 
    def __new__(self, n): 
    	## On retourne l'angle principale dans l'intervalle [0;360] 
        return int.__new__(self, n % 360) 
    def __sub__(self, n): 
    	## On calcule la différence de 2 angles en retournant l'angle principal 
        return angle(super(angle, self).__sub__(n)) 
    def __add__(self, n): 
    	## On calcule la somme de 2 angles en retournant l'angle principal     
        return angle(super(angle, self).__add__(n)) 
  
A = angle(540) 
B  = angle(- 460) 
print A, B, type(A), type(B)  ## 180 260 <class '__main__.angle'> <class '__main__.angle'> 
print A - B, type(A - B)	  ## 280 <class '__main__.angle'> 
print A + B, type(A - B)	  ## 80 <class '__main__.angle'>

Mis à jour le 29 novembre 2006 Guigui_

En Python, on peut surcharger tous les opérateurs. L'ensemble de ces opérateurs est identique à ceux que l'on retrouve dans le module operator . Ces opérateurs se redéfinissent donc dans une classe de la manière suivante def __operateur__(self, ...): ...
Dans l'exemple suivant, nous allons créer une classe Vecteur et définir les opérations habituelles sur un vecteur

Code python :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
# -*- coding: cp1252 -*- 
import math 
  
class Vector: 
    def __init__(self, x=0, y=0): 
        self.x=x 
        self.y=y 
    def __eq__(self, vB): return (self.x==vB.x) and (self.y==vB.y)    ## test l'égalité de 2 vecteurs         
    def __add__(self, vB):  return Vector(self.x+vB.x,self.y+vB.y)  ## retourne le vecteur somme 
    def __sub__(self, vB):  return Vector(self.x-vB.x,self.y-vB.y) ## retourne le vecteur différence 
    def __mul__(self, c): 
        if isinstance(c,Vector): return  self.x*c.x+self.y*c.y ## retourne le produit scalaire 
        else: return Vector(c*self.x,c*self.y) ## retourne le vecteur multiplé par un scalaire 
    def __div__(self, c): return Vector(self.x/c, self.y/c) ## retourne le vecteur ayant subi une division scalaire 
    def __abs__(self): return math.hypot(self.x, self.y) ## retourne la norme2 du vecteur 
    def __str__(self): return '('+str(self.x)+','+str(self.y)+')' ## retourne la réprésentation du vecteur sous forme d'une chaîne 
  
>>> a = Vector(4,5) 
>>> b = Vector(6,7) 
>>> print a==b 
False 
>>> print a+b 
(10,12) 
>>> print a-b 
(-2,-2) 
>>> print a*b 
59 
>>> print abs(a) 
6.40312423743

Mis à jour le 19 septembre 2006 Guigui_

Proposer une nouvelle réponse sur la FAQ

Ce n'est pas l'endroit pour poser des questions, allez plutôt sur le forum de la rubrique pour ça


Réponse à la question

Liens sous la question
précédent sommaire suivant
 

Les sources présentées sur cette page sont libres de droits et vous pouvez les utiliser à votre convenance. Par contre, la page de présentation constitue une œuvre intellectuelle protégée par les droits d'auteur. Copyright © 2014 Developpez Developpez LLC. Tous droits réservés Developpez LLC. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents et images sans l'autorisation expresse de Developpez LLC. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.

 
 
 
 
Partenaires

PlanetHoster
Ikoula