J'ai besoin d'aide pour trouver une solution à une fuite de mémoire que j'ai. J'ai une application C # (.NET V3.5) permettant à un utilisateur d'exécuter des scripts IronPython à des fins de test. Les scripts peuvent charger différents modules de la bibliothèque standard Python (comme inclus avec des binaires Ironthon). Cependant, lorsque le script est terminé, la mémoire allouée aux modules importés n'est pas recueillie. La boucle via plusieurs pistes d'un script (effectuée pour le test de contrainte) provoque une utilisation du système de mémoire pendant une utilisation à long terme.
Voici une version simplifiée de ce que je fais. P>
classe de script Fonction principale: p> un exemple de script "test.py" qui charge le module aléatoire (ajoute ~ 1500 Ko de mémoire): p> Un mécanisme de boucle qui provoquera l'exécution du système de la mémoire: p> J'ai ajouté la section pour ne pas optimiser la compilation en fonction de ce que j'ai trouvé dans < un href = "http://lists.ironpython.com/pipermarmail/users-ironpython.com/2009-janaire/009396.html" rel = "Noreferrer"> Ce thread , mais la fuite de mémoire se produit de toute façon . Ajout de l'appel explicite à S.Dispose () ne fait pas non plus de différence (comme prévu). J'utilise actuellement IronPython 2.0, mais j'ai aussi essayé de passer à IronPython 2.6 RC2 sans aucun succès. P> Comment puis-je obtenir les modules importés dans le script IRDYPYTHON intégré pour être déposé comme la normale .NET objets lorsque le moteur de script / runtime est hors de portée? p> p>
3 Réponses :
Avez-vous essayé de courir le Python de fer dans sa propre appdomaine? Python.createngine vous permet de transmettre une appdomaine, qui peut ensuite être déchargée lorsque le script est terminé.
ou, basé sur Cette discussion, utilisez une option LightweightScopes, comme P>
Dictionary<String, Object> options = new Dictionary<string, object>(); options["LightweightScopes"] = true; ScriptEngine engine = Python.CreateEngine(options); ScriptRuntime runtime = engine.Runtime;
Simple et efficace en tant que solution de contournement, j'avais négligé cela. En forçant l'appdomain à décharger, la fuite de mémoire est contrôlée (bien que mon empreinte globale ait augmenté en utilisant une Appdomain).
Bonne réponse, mais je vais garder cela ouverte pendant une journée ou deux pour voir si quelqu'un a une solution pouvant résoudre le problème, car il s'agit vraiment d'une solution de contournement.
Lescopes léger ne fonctionnent pas. Sur la base de la discussion que vous avez liée, il ne résout probablement que le problème de recharger un module dans un script où il est déjà chargé. Mon problème est la collection des ordures qui ne se produit pas lorsque le script est terminé. Cependant, je ne serais toutefois pas surpris si les deux problèmes ont la même cause première de la DLR.
J'ai recréé ce que je pense que vous faites, et mon utilisation de la mémoire monte à 70 000 km environ, mais n'a pas disparu plus haut. Combien de temps est-il utilisé à long terme?
Quelle version Ironpython utilisez-vous? Le mien peut grimper à 120 000 en cinq minutes environ et ne jamais se limiter vraiment. L'utilisation à long terme pourrait être aussi longue que quelques jours ou plus dans le cas des tests de stress.
On dirait que vous pouvez être sur une solution légitime, car la solution d'AppDomain se limitent à environ 64 000 km, de sorte que 70 000 000 sont certainement dans la gamme.
Je devrais être plus précis, j'utilise la partie légerScopes. Sans que l'option a permis à ma mémoire construit rapidement, avec elle sur elle construit jusqu'à un seuil puis des niveaux.
Pourriez-vous mettre votre code dans une nouvelle réponse? J'essaie l'option LightWeightScopes et ma mémoire est une construction régulière (plus de 165 000 000 et escalade après cinq minutes, car je tape ceci)
Aha! Pyopts ["Lightweightscopes"] = ScripstingRuntimeHelPers.True fonctionne à IronPython 2.6, mais Pyopts ["" LightweightScopes "] = true ne pas dans ironpython 2.0 (peut-être parce que ScriptingRuntimeHelPers n'est pas défini pour cette version de l'Assemblée Microsoft.Scripting).
à l'aide de fer python 2.6 RC 2 et C # 3.5 et ma boucle est p> l'utilisation de la mémoire augmente à environ 70 000K , mais puis les niveaux off. p> p>
Oui, cela fonctionne simplement bien avec IronPython 2.6 RC2. Mais cela n'a pas fonctionné avec IronPython 2.0.1. Malheureusement, 2.6 RC2 a du mal à importer des variables à l'espace de noms global. Je vais essayer 2.0.3 et poster des résultats. Merci du coup de main jusqu'à présent :)
L'autre réponse ne m'a pas beaucoup aidé, alors je pose ma solution de contournement. Ce que j'ai fait est que j'ai mis en place la portée de script et le moteur en dehors de ma boucle. Ma future de la mémoire augmentait très vite avant, mais avec ce correctif, j'ai pu l'arrêter.
La seule chose que je suis restée à l'intérieur de la boucle était l'appel de mon script Python. C'est le début de mon script. P>
var result= scope.GetVariable("MyPythonMethod");