J'ai du mal à charger un fichier mariné dans un module différent du module où j'ai mariné le fichier. Je connais le fil suivant: Impossible de charger des fichiers à l'aide de modules de pickle et multipile . J'ai essayé la solution proposée d'importer la classe dans le module où je décompresse mon fichier, mais cela me donne toujours la même erreur: AttributeError: Can't get attribute 'Document' on <module '__main__' from ''>
La structure de base de ce que j'essaie de faire:
Utilisez un fichier qui décapage et décompresse des objets, utils.py:
import pickle
def save_document(doc):
from class_def import Document
write_file = open(file_path, 'wb')
pickle.dump(doc, write_file)
def load_document(file_path):
from class_def import Document
doc_file = open(file_path, 'rb')
return pickle.load(doc_file)
Fichier dans lequel l'objet Document est défini et la méthode save util est appelée, class_def.py:
import utils
class Document(object):
data = ""
if __name__ == '__main__':
doc = Document()
utils.save_document(doc)
Fichier où la méthode de chargement est appelée, process.py:
import utils
if __name__ == '__main__':
utils.load_document(file_path)
L'exécution de process.py donne l'attributError mentionné. Si j'importe le fichier class_def.py dans process.py et que j'exécute sa méthode principale comme mentionné dans le thread d'origine, cela fonctionne, mais je veux pouvoir exécuter ces deux modules séparément, car le fichier class_def est une étape de prétraitement qui prend tout à fait parfois. Comment pourrais-je résoudre ce problème?
dans ton class_def.py
fichier vous avez ce code:
if __name__ == '__main__':
doc = Document()
utils.save_document(doc)
Cela signifie que doc
sera un __main__.Document
objet, donc quand il est mariné, il s'attend à pouvoir obtenir une classe Document
à partir du module principal, pour résoudre ce problème, vous devez utiliser la définition de Document
à partir d'un module appelé class_def
ce qui signifie que vous ajouteriez une importation ici:
if __name__ == '__main__':
from class_def import Document
# ^ so that it is using the Document class defined under the class_def module
doc = Document()
utils.save_document(doc)
de cette façon, il devra exécuter le fichier class_def.py deux fois, une fois en tant que __main__
et une fois comme class_def
mais cela signifie que les données seront décapées en tant que class_def.Document
objet donc le charger récupérera la classe du bon endroit. Sinon, si vous avez un moyen de construire un objet document à partir d'un autre, vous pouvez faire quelque chose comme ça dans utils.py
:
def save_document(doc):
if doc.__class__.__module__ == "__main__":
from class_def import Document #get the class from the reference-able module
doc = Document(doc) #convert it to the class we are able to use
write_file = open(file_path, 'wb')
pickle.dump(doc, write_file)
Bien que d'habitude, je préfère la première façon.
J'ai eu un problème similaire et je viens juste de réaliser les différences entre nos implémentations.
Votre structure de fichiers:
Mon erreur (en utilisant vos noms de fichiers) était la première:
Ce qui a résolu mon problème d'importation de cornichons:
Cela a eu l'effet secondaire bienvenu que je n'avais pas besoin d'importer le fichier util_and_class car il est cuit dans le fichier pickle. L'appel de l'instance et l'enregistrement du cornichon dans un fichier séparé ont résolu le __name__
problème de "chargement d'un fichier décapé dans un module différent du module dans lequel j'ai décapé le fichier."