Un modèle de codage commun utilisé en AML était d'exécuter un AML (avec paramètres) dans un autre AML.
Une application que je développe actuellement gagnerait à pouvoir exécuter un script Python (avec paramètres) dans un autre script Python.
Cependant, cela ne semble pas du tout simple.
En utilisant ArcGIS 10, j'expérimente avec l'encapsulation du script Python "interne" dans un outil ArcGIS qui a les paramètres. Je pensais que ce serait une question simple que le script Python "externe" utilise arcpy.ImportToolbox pour importer la boîte à outils, puis exécuter le ou les outils à l'intérieur. Cependant, jusqu'à présent, toutes mes tentatives pour exécuter l'outil "interne" à partir du script "externe" semblent simplement ignorer l'outil "interne" (aucune erreur n'est levée).
Voici du code de test pour mieux illustrer ce que j'essaie de décrire.
Mon script testinner.py est:
inputString = arcpy.GetParameterAsText(0)
newFC = "C:\\Temp\\test.gdb\\" + inputString
arcpy.Copy_management("C:\\Temp\\test.gdb\\test",newFC)
Mon script testouter.py est:
import arcpy
inputString1 = arcpy.GetParameterAsText(0)
inputString2 = arcpy.GetParameterAsText(1)
arcpy.ImportToolbox("C:\\Temp\\test.tbx")
arcpy.testinner_test(inputString1)
arcpy.testinner_test(inputString2)
Pour testinner.py, son outil a besoin d'un seul paramètre String.
Pour testouter.py, son outil a besoin de deux paramètres String
Les deux outils sont placés dans un test.tbx.
Le test.gdb a juste besoin d'une seule classe d'entités vide appelée test.
Une fois que vous avez assemblé ce qui précède, l'exécution de l'outil testinner avec une chaîne comme 'abc' transmise comme paramètre devrait entraîner la copie de la classe d'entités 'test' dans une autre appelée 'abc' OK.
Mais lorsque vous essayez d'exécuter l'outil testouter avec deux chaînes comme «uvw» et «xyz» comme paramètres, l'outil testinner dans testouter.py semble fonctionner correctement une fois, mais envoie ArcMap 10 SP2 sur Vista SP2 à une grave erreur d'application lorsque essayer de l'utiliser la deuxième fois.
Le même test avec Windows XP SP3 et ArcGIS Desktop 10 SP2 génère également une erreur d'application grave au même point.
Réponses:
Voici votre exemple de test modifié pour importer un module "utilitaire" dans le script principal et appeler une fonction en utilisant les paramètres lus par l'outil de script:
CopyFeaturesTool.py - Outil de script qui lit les paramètres et appelle une fonction dans un autre module
CopyFeaturesUtility.py - Module qui a une seule fonction
copyFeaturesToTempGDB
. Peut être importé ou exécuté de façon autonome. S'il est exécuté de manière autonome, le code sousif __name__ == '__main__'
est exécuté.Je pense que vous trouverez cette approche modulaire beaucoup plus efficace et logique une fois que vous vous y serez habitué. La section Modules du didacticiel Python standard est également une bonne ressource pour comprendre le fonctionnement de l'importation.
Pour des exemples plus spécifiques à arcpy, jetez un œil aux scripts intégrés dans votre
C:\Program Files\ArcGIS\Desktop10.0\ArcToolbox\Scripts
dossier.la source
Vous pouvez accomplir cela en important un module (ie un script) dans votre script principal et en appelant ses fonctions. Une démonstration simple est contenue dans les deux scripts d'accompagnement.
pour le programme principal et pour les fonctions qui sont appelées
il vous suffit de vous assurer que le module principal et le module enfant sont dans le même dossier. Vous pouvez facilement transmettre des paramètres au module enfant et si le module enfant a besoin d'accéder à arcpy (en supposant que vous utilisez la version 10 d'arcmap), transmettez-lui simplement une référence.
la source
L'importation et l'exécution d'une fonction est la façon la plus propre de le faire, mais pour être complet, il y a aussi la
execfile
fonction intégrée ( documentation ) qui vous permettra d'exécuter un fichier arbitraire dans le contexte actuel.la source
La méthode execfile décrite par @JasonScheirer m'a permis de réorganiser mon code en celui ci-dessous et fournit une solution à mon problème de test:
Cependant, cela peut s'avérer lourd lorsqu'il est appliqué à des scripts non-test qui sont beaucoup plus longs, j'ai donc utilisé le travail de @ blah238 qui a approuvé l'approche de @ DanPatterson et est venu avec le code final (test) suivant qui fait exactement ce dont j'ai besoin.
et
la source