2

pyzoのバージョンを簡単に起動できるようにpython3.3、新しいエイリアスを 1 つ追加しました。.bash_profilepython3.3

このエイリアスを端末で問題なく使用できますが、 のようなものを使用するとsubprocess.check_call(args = ["python3.3", onePyFile])、次のエラーが発生します。

Traceback (most recent call last):
  ...
  File "/Library/Frameworks/pyzo2013b/lib/python3.3/subprocess.py", line 540, in check_call
    retcode = call(*popenargs, **kwargs)
  File "/Library/Frameworks/pyzo2013b/lib/python3.3/subprocess.py", line 521, in call
    with Popen(*popenargs, **kwargs) as p:
  File "/Library/Frameworks/pyzo2013b/lib/python3.3/subprocess.py", line 818, in __init__
    restore_signals, start_new_session)
  File "/Library/Frameworks/pyzo2013b/lib/python3.3/subprocess.py", line 1416, in _execute_child
    raise child_exception_type(errno_num, err_msg)
FileNotFoundError: [Errno 2] No such file or directory: 'python3.3'

私のエイリアスはどこにも見られないと思います。では、どうすれば問題を解決できますか? 自分のエイリアスを作成する良い方法は何ですか?

を試してみるとsubprocess.check_call(args = ["python3.3", onePyFile], shell = True)、次のエラーが発生します。

onePyFile.py: python3.3: command not found
Traceback (most recent call last):
  File "mainFile.py", line 72, in <module>
    shell = True
  File "/Library/Frameworks/pyzo2013b/lib/python3.3/subprocess.py", line 545, in check_call
    raise CalledProcessError(retcode, cmd)
subprocess.CalledProcessError: Command '['python3.3', 'onePyFile.py']' returned non-zero exit status 127

subprocess.check_call(args = ["python3.3", onePyFile])where the first line onePyFileisだけを使用する#! /usr/bin/env python3.3と、次のエラーが発生します。

env: python3.3: No such file or directory
Traceback (most recent call last):
  ...

私の問題は、Python 呼び出しよりもシンボリック リンクに関するものだと思います。しかし、何が悪いのかわかりません。実際、エイリアスを使用して個人的なシンボリック リンクを作成するのはこれが初めてです。

4

3 に答える 3

5

試すsubprocess.check_call(args = ["python3.3", onePyFile] , shell=True, env={'ENV':path_of_bash_profile})

shell が True の場合、指定されたコマンドがシェルを通じて実行されます。これは、ほとんどのシステム シェルで提供される強化された制御フローのために主に Python を使用していて、シェル パイプ、ファイル名のワイルドカード、環境変数の展開、ユーザーのホームへの ~ の展開などの他のシェル機能に便利にアクセスしたい場合に便利です。ディレクトリ。ただし、Python 自体が多くのシェルのような機能 (特に、glob、fnmatch、os.walk()、os.path.expandvars()、os.path.expanduser()、および shutil) の実装を提供していることに注意してください。

于 2013-10-20T14:02:35.917 に答える
3

これは、 subprocess がデフォルトでシェルをロードしないため ( docsを参照)、.bash_profile の内容を取得できないためです。これを使って:

subprocess.check_call(args = ["python3.3", onePyFile], shell=True)

編集:グラスリオンは私より速かったようです!

編集 2: もう少し掘り下げてみたところ、奇妙なことがわかりました。shell=True が期待どおりに機能しないように見えたので、bash を直接呼び出す、より直接的なアプローチを取りました。

a.py:

from subprocess import check_call
check_call(['bash', '-c', '. ~/.bash_profile && ABC a bc'])

a.sh (python3 実行可能ファイル):

echo $*

私は最初にで試しましalias ABC='~/Documents/a.sh'.bash_profile

$ python ~/Documents/a.py
bash: ABC: command not found
Traceback (most recent call last):
  File "Documents/a.py", line 6, in <module>
    check_call(['bash', '-c', '. ' + expanduser('~/.bash_profile') + ' && ABC a bc'])
  File "/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/subprocess.py", line 511, in check_call
subprocess.CalledProcessError: Command '['bash', '-c', '. ~/.bash_profile && ABC a bc']' returned non-zero exit status 127

次に、エイリアスから関数に切り替えましたABC() { ~/Documents/a.sh $*; }

$ python ~/Documents/a.py
a bc

要するに、動作するようになったのですが、理由がわかりません! シェルは信頼できないため、シェルをスキップするのが最善です。

シバンの原理 (フレッド・ミッチェルが提案したように) を巧妙な方法で使用することで、これを行うことができます。

from subprocess import check_call
check_call(['/usr/bin/env', 'python3', onePyFile])

これは、Python 3 が正しくインストールされていれば、そのパスとは関係なく機能します (あなたが達成したかったと思います)。

于 2013-10-20T14:03:38.880 に答える
0

onePyFile の最初の行に python3.3 へのシバンを入れて、python の実行を明示的に省略しないのはなぜですか?

于 2013-10-20T14:06:11.620 に答える