2016-10-10 1 views
2

Cela doit avoir une réponse, mais je ne peux pas le trouver. J'utilise un assez grand module python appelé quippy. Avec ce module, on peut définir un potentiel intermoléculaire à utiliser comme une calculatrice ASE comme ceci:Comment éviter réimporter modules et redéfinissant grand objet chaque fois qu'un script est exécuté

from quippy import * 
from ase import atoms 
pot=Potential("Potential xml_label=gap_h2o_2b_ccsdt_3b_ccsdt",param_filename="gp.xml") 
some_structure.set_calculator(pot) 

C'est le début d'un script. Le problème est que le import prend environ 3 secondes et pot=Potential... prend environ 30 secondes avec 100% de la charge du processeur. (Je crois que cela est dû à l'analyse d'un grand fichier xml ascii.) Si je devais taper interactivement je pourrais garder le module importé et le potentiel défini, mais lors de l'exécution du script, il est fait à chaque exécution.

Puis-je enregistrer le module et l'objet potentiel en mémoire/disque entre pistes? Peut-être garder un processus python au ralenti et garder ces choses en mémoire? Ou exécutez ces lignes dans l'interpréteur et d'une manière ou d'une autre appelez le reste du script à partir de là?

Toute approche est très bien, mais un peu d'aide est appréciée!

+0

Comment sont souvent vous appelle le script? Si vous avez suffisamment de RAM, votre système d'exploitation mettra en cache les fichiers de module utilisés pendant 'import'. Si vous voulez stocker 'pot', il suffit de l'écrire dans un fichier, par exemple. en utilisant 'pickle'. – MisterMiyagi

Répondre

0

Vous pouvez utiliser des fichiers bruts ou des modules tels que pickle pour stocker facilement des données.

import cPickle as pickle 
from quippy import Potential 
try: # try previously calculated value 
    with open('/tmp/pot_store.pkl') as store: 
     pot = pickle.load(store) 
except OSError: # fall back to calculating it from scratch 
    pot = quippy.Potential("Potential xml_label=gap_h2o_2b_ccsdt_3b_ccsdt",param_filename="gp.xml") 
    with open('/tmp/pot_store.pkl', 'w') as store: 
     pot = pickle.dump(pot, store) 

Il existe différentes optimisations à cela, par ex. vérifier si votre fichier pickle est plus ancien que le fichier générant sa valeur.

+0

Je vais essayer wthis avec votre code, mais j'ai juste essayé avec cPickle et je n'ai pas réussi à le faire fonctionner. Mais que voulez-vous dire avec des fichiers bruts? L'enregistrer comme un binaire ferait l'affaire, je pense, mais comment? –

+0

Que voulez-vous dire par "ne l'ai pas fait fonctionner"? Cela fait partie de la bibliothèque standard py2.7. Les fichiers bruts ne sont que des fichiers sur lesquels vous écrivez des chaînes sans aucune bibliothèque. Par exemple, si 'pot' est un float, vous pouvez faire' store.write (str (pot)) 'et' float (store.readline(). Strip()) '. – MisterMiyagi

+0

Je n'étais pas bien formulé. cPickle n'a pas donné d'erreur, ni lors du chargement ni lors du chargement, mais en essayant d'exécuter le potentiel chargé, j'ai eu une erreur. Et en regardant le fichier, il y avait quelques octets, pas près de la taille de l'objet réel. –

0

je trouve une solution, mais je suis intéressé par des solutions de rechange. Vous pouvez diviser le script en deux parties:

start.py:

from quippy import Potential 
from ase import atoms 
pot=Potential(... etc... 

body.py:

for i in range(max_int): 
     print "doing things" 
# etc... 

Entrez ensuite interpréteur Python et exécuter une seule fois le script de démarrage mais le corps autant que nécessaire:

[email protected]:~/dir$ python 
>>> execfile('start.py') 
>>> execfile('body.py') 
>>> #(change code of "body.py" in editor) 
>>> execfile('body.py') # again without reloading "start.py" 

Cela signifie qu'un terminal est occupé et que le script est affecté, mais rks.