エラーメッセージを表示せずに早期終了するために、arcpyスクリプトでsys.exit(0)を使用するにはどうすればよいですか?


13

ArcGIS 10.0用のarcpyツールスクリプトには、2つの主要な機能セクションがあります。ユーザーは、2番目のセクションを実行するかどうかを選択できます。ユーザーが2番目のセクションを実行しないことを選択した場合、ツール結果ウィンドウにエラーメッセージを表示せずに、クリーンアップ関数を実行してsys.exit(0)でスクリプトを終了するだけです GIS-SEにはarcpyスクリプトの終了に関する2つの主要なスレッドがありますが、そのソリューションはエラーメッセージを具体的に扱っていません。コードの一般的な構造は次のとおりです。

import sys
##import arcpy

def CleanUp():
    print 'Cleaning up ...\n'

def finish():
    CleanUp()
    print 'Exiting ...'
    sys.exit(0)

do_more = False  #or True ... input from user

#Section 1:  do some stuff
print 'Doing some stuff ...\n'

if not do_more:
    finish()

#Section 2:  do more stuff
print 'doing more stuff ...'
CleanUp()

このコードをArcGIS / arcpyの外部のPythonインタープリターで実行すると、期待どおりに動作し、エラーメッセージなしで正常に終了します。ただし、この同じ構造のarcpyスクリプトでは、スクリプトは終了しますが、SystemExitエラーメッセージがツールの結果ウィンドウに表示されます。arcpyツールスクリプトに例外を食べさせ、SystemExitエラーメッセージを埋める方法はありますか?


ここでワイルドな突き刺しをしただけですが、スクリプトでSystemExitを呼び出す前に「アークピーを削除」することは可能ですか?

@ダン-私はそれを疑いますが、それは興味深いアイデアです...うーん...一体何。私はそれに旋回を与えます。
ケルトフルート

1
ロジックを明確に示し、余分なものを省いた簡潔なコード例を投稿していただきありがとうございます。+1
マットウィルキー

回答:


8

短い答え:10.1で修正されました。今のところ、インデントのレベルを追加する必要があります。ただし、これにより、コードの便利なリファクタリングが促進される場合があります。1つのスクリプト/ルーチンで多数の行を取得する場合は、いつでもそれを小さなセクション(関数、クラス)に分割することを検討する必要があります。

def main():
    <your code>

if __name__ == "__main__":
    try:
        main()
    except SystemExit as err:
        pass

ありがとう、ジェイソン。はい、弾丸を噛んでリファクタリングする必要があります。クライアントが私の首を呼吸することでそれを行うのは難しいです。それが人生だ。
ケルトフルート

3

ArcPyはPython環境を混乱させます。要するに、sys.exit()を呼び出す前に、sys.exit()を実行しないか、arcpyの「終了前のクリーンアップ」関数(存在する場合)を検索/呼び出ししないでください。


2
Pythonの実行可能ファイルの処理方法sys.exit()は一種の汚いトリックです。呼び出しexitSystemExit例外を発生させ、通常はトレースバックを出力するトップレベルインタープリターが例外タイプを検出し、インタープリターを終了します。ArcGISファミリーの実行可能ファイルなど、別のアプリケーションにPythonインタープリターを埋め込むには、このような実装固有のコードが自明ではありません。
ジェイソンシャイラー

2

SystemExitエラーメッセージを「埋める」方法はわかりませんが、sys.exitの呼び出しを避けるためにコードをいつでも再構築できます

import sys
##import arcpy

def DoMoreStuff():
    print 'doing more stuff ...'

def CleanUp():
    print 'Cleaning up ...'

def finish():
    CleanUp()
    print 'Exiting ...'

do_more = False  #or True ... input from user

#Section 1:  do some stuff
print 'Doing some stuff ...'

if do_more:DoMoreStuff()

finish()

確かに、私のarcpyスクリプトの2つのセクションはかなり巨大です。私はむしろ別のレベルのインデントを作成せず、結果として生じるスコーピングの問題に対処する必要があります...しかし、はい、これは解決策になります。本当にイライラするのは、arcpyでsys.exitを使用した場合にのみエラーメッセージが表示されることです。通常のPythonでは、SystemExit例外はエラーと見なされないため、メッセージは投稿されません。
ケルトフルート
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.