私はこのコードを持っています:
def hello():
return 'Hi :)'
これをコマンドラインから直接実行する方法を教えてください。
-c
(コマンド) 引数を使用する(ファイルの名前がfoo.py
であると仮定します)。
$ python -c 'import foo; print foo.hello()'
あるいは、名前空間の汚染を気にしないのであれば、
$ python -c 'from foo import *; print hello()'
そして真ん中は:
$ python -c 'from foo import hello; print hello()'
hello()
を関数の下のどこかに置くだけで、python your_file.py
を実行したときに実行されます。
より良い解決策のためにあなたはこれを使うことができます:
if __== '__main__':
hello()
そうすれば、ファイルをインポートしたときではなく、ファイルを実行したときにだけ関数が実行されます。
python -c 'from myfile import hello; hello()'
ここでmyfile
はあなたのPythonスクリプトのベース名に置き換えなければなりません。 (例:myfile.py
はmyfile
になります)。
ただし、hello()
がPythonスクリプトの「永続的」なメインエントリポイントである場合、これを行う通常の方法は次のとおりです。
def hello():
print "Hi :)"
if __== "__main__":
hello()
これにより、python myfile.py
またはpython -m myfile
を実行するだけでスクリプトを実行できます。
__name__
は現在実行されているモジュールの名前を保持する特別なPython変数です。 モジュールがコマンドラインから起動された場合は を除いて、"__main__"
になります。
私はbashのコマンドラインから呼び出せる簡単で小さなPythonスクリプトを書きました。呼び出したいモジュール、クラス、メソッドの名前と、渡したいパラメータを取ります。私はそれをPyRunと呼び、.py拡張子を省き、chmod + x PyRunで実行可能にしました。
./PyRun PyTest.ClassName.Method1 Param1
これをPyRunというファイルに保存してください。
#!/usr/bin/env python
#make executable in bash chmod +x PyRun
import sys
import inspect
import importlib
import os
if __== "__main__":
cmd_folder = os.path.realpath(os.path.abspath(os.path.split(inspect.getfile( inspect.currentframe() ))[0]))
if cmd_folder not in sys.path:
sys.path.insert(0, cmd_folder)
# get the second argument from the command line
methodname = sys.argv[1]
# split this into module, class and function name
modulename, classname, funcname = methodname.split(".")
# get pointers to the objects based on the string names
themodule = importlib.import_module(modulename)
theclass = getattr(themodule, classname)
thefunc = getattr(theclass, funcname)
# pass all the parameters from the third until the end of
# what the function needs & ignore the rest
args = inspect.getargspec(thefunc)
z = len(args[0]) + 2
params=sys.argv[2:z]
thefunc(*params)
これがどのように機能するかを示すためのサンプルモジュールです。これはPyTest.pyというファイルに保存されます。
class SomeClass:
@staticmethod
def First():
print "First"
@staticmethod
def Second(x):
print(x)
# for x1 in x:
# print x1
@staticmethod
def Third(x, y):
print x
print y
class OtherClass:
@staticmethod
def Uno():
print("Uno")
これらの例を実行してみてください。
./PyRun PyTest.SomeClass.First
./PyRun PyTest.SomeClass.Second Hello
./PyRun PyTest.SomeClass.Third Hello World
./PyRun PyTest.OtherClass.Uno
./PyRun PyTest.SomeClass.Second "Hello"
./PyRun PyTest.SomeClass.Second \(Hello, World\)
Secondメソッドの唯一のパラメータとしてTupleを渡すために括弧をエスケープする最後の例に注意してください。
メソッドが必要とするものに対してあまりにも少ないパラメータを渡すと、エラーになります。あなたがあまりにも多くを渡した場合、それはエキストラを無視します。モジュールは現在の作業フォルダになければなりません、PyRunはあなたのパスのどこにでも置くことができます。
このスニペットをスクリプトの最後に追加してください
def myfunction():
...
if __== '__main__':
globals()[sys.argv[1]]()
あなたは今実行することによってあなたの関数を呼び出すことができます
python myscript.py myfunction
これは、コマンドライン引数(関数名の文字列)を現在のローカルシンボルテーブルを持つ辞書であるlocals
に渡しているためです。最後の括弧は関数を呼び出すようにします。
update: もしあなたがコマンドラインからパラメータを受け付けるようにしたいのなら、sys.argv[2]
を次のように渡してください。
def myfunction(mystring):
print mystring
if __== '__main__':
globals()[sys.argv[1]](sys.argv[2])
このようにしてpython myscript.py myfunction "hello"
を実行するとhello
が出力されます。
私たち自身でこれをもう少し簡単にして、ただモジュールを使用しましょう。
試してみてください:pip install compago
それから書く:
import compago
app = compago.Application()
@app.command
def hello():
print "hi there!"
@app.command
def goodbye():
print "see ya later."
if __== "__main__":
app.run()
それならこんな風に使ってください:
$ python test.py hello
hi there!
$ python test.py goodbye
see ya later.
注:現時点ではPython 3には bug がありますが、Python 2ではうまく機能します。
編集: 私の意見では、グッドのモジュール fire を使うのがさらに良い選択肢です。これにより、関数の引数も簡単に渡すことができます。 pip install fire
と一緒にインストールされます。彼らのGitHubから:
これは簡単な例です。
import fire
class Calculator(object):
"""A simple calculator class."""
def double(self, number):
return 2 * number
if __== '__main__':
fire.Fire(Calculator)
次に、コマンドラインから次のコマンドを実行します。
python calculator.py double 10 # 20
python calculator.py double --number=15 # 30
面白いことに、コマンドラインコンソールに出力すること、またはその他の細かいpython操作を実行することが目的であれば、入力を次のようにpythonインタプリタに渡すことができます。
echo print("hi:)") | python
パイプファイルと同様に。
python < foo.py
*拡張子が2番目に機能するために.pyである必要はないことに注意してください。 **またbashのためにあなたは文字をエスケープする必要があるかもしれないことに注意してください
echo print\(\"hi:\)\"\) | python
pip install runp
を指定してrunpパッケージをインストールすると、実行の問題になります。
runp myfile.py hello
リポジトリは次の場所にあります。 https://github.com/vascop/runp
私はコマンドラインでさまざまなpythonユーティリティ(range、stringなど)を使う必要があり、そのために pyfunc というツールを書いていました。あなたはあなたにコマンドライン使用経験を豊かにするためにそれを使うことができます:
$ pyfunc -m range -a 1 7 2
1
3
5
$ pyfunc -m string.upper -a test
TEST
$ pyfunc -m string.replace -a 'analyze what' 'what' 'this'
analyze this
このようなもの:call_from_terminal.py
# call_from_terminal.py
# Ex to run from terminal
# ip='"hi"'
# python -c "import call_from_terminal as cft; cft.test_term_fun(${ip})"
# or
# fun_name='call_from_terminal'
# python -c "import ${fun_name} as cft; cft.test_term_fun(${ip})"
def test_term_fun(ip):
print ip
これはbashで機能します。
$ ip='"hi"' ; fun_name='call_from_terminal'
$ python -c "import ${fun_name} as cft; cft.test_term_fun(${ip})"
hi
コマンドラインで python というコマンドでpythonを入力することは常にオプションです。
次にファイルをインポートします。 import example_file
それから example_file.hello() を指定してコマンドを実行します。
これにより、python -cなどを実行するたびに生成される奇妙な.pycコピー機能が回避されます。
たぶん、シングルコマンドほど便利ではないかもしれませんが、コマンドラインからファイルをテキスト化するための良い素早い修正で、pythonを使ってファイルを呼び出して実行することを可能にします。
以下は、関数の定義を含むOdd_Even_function.pyファイルです。
def OE(n):
for a in range(n):
if a % 2 == 0:
print(a)
else:
print(a, "ODD")
今コマンドプロンプトから同じことを呼ぶために今私のために働いたオプションがあります。
オプション1 exeの絶対パス\ python.exe -c "import Odd_Even_function; Odd_Even_function.OE(100)"
オプション2 exe\python.exe -cのフルパス "Odd_Even_function import OEから; OE(100)"
ありがとう。
この関数はコマンドラインから実行することはできません。手を加えないで値が返されるためです。あなたはリターンを削除し、代わりにprintを使うことができます