web-dev-qa-db-ja.com

Python組み込み関数「コンパイル」。何のために使用されますか?

今日、組み込み関数 compile に出会いました。私はドキュメントを読みましたが、それがその使用法またはそれが適用される場所をまだ理解していませんが。誰でもこの機能の使用例を説明できますか。例を本当に感謝します。

ドキュメントから、関数は以下に示すようにいくつかのパラメーターを取ります。

compile(source, filename, mode[, flags[, dont_inherit]])
35
demo.b

一般的に使用されているものではありません。文字列形式のPythonソースコードがあり、それを保持して使用できるPythonコードオブジェクトにする場合に使用します。簡単な例を次に示します。

_>>> codeobj = compile('x = 2\nprint "X is", x', 'fakemodule', 'exec')
>>> exec(codeobj)
X is 2
_

基本的に、コードオブジェクトは文字列をオブジェクトに変換します。オブジェクトは後でexec onを呼び出して、文字列内のソースコードを実行できます。 (これは「exec」モード用です。「eval」モードでは、文字列に単一の式のコードが含まれている場合、代わりにevalを使用できます。)これは一般的なタスクではないため、決して遭遇することはありませんそれの必要性。

主な用途は、メタプログラミングまたは埋め込みの状況です。たとえば、ユーザーがカスタムPythonコードでその動作をスクリプト化できるPythonプログラムがある場合、compileおよびexecを使用して、これらのユーザー定義スクリプトを実行します。

compileがほとんど使用されないもう1つの理由は、execeval、およびそれらのilk、compileが潜在的なセキュリティホールであることです。ユーザーコードを文字列形式で取得してコンパイルし、後で実行すると、安全でないコードを実行している可能性があります。 (たとえば、上の例では、コードが_print x_ではなくformatYourHardDrive()であったと想像してください。)

52
BrenBarn

compileは、execおよびevalの下位バージョンです。ステートメントや式を実行または評価することはありませんが、それを実行できるコードオブジェクトを返します。モードは次のとおりです。

  1. compile(string, '', 'eval')は、eval(string)を実行した場合に実行されるコードオブジェクトを返します。このモードではステートメントを使用できないことができないことに注意してください。 (単一の)式のみが有効です。単一の式に使用されます。
  2. compile(string, '', 'exec')は、exec(string)を実行した場合に実行されるコードオブジェクトを返します。ここでは、任意の数のステートメントを使用できます。モジュール全体に使用されます。
  3. compile(string, '', 'single')execモードに似ていますが、最初のステートメント以外のすべてを無視します。 if/elseステートメントとその結果は、単一のステートメントと見なされることに注意してください。単一のステートメントに使用されます。

ドキュメント を見てください。 http://joequery.me/code/python-builtin-functions/#compile にも素晴らしい(まあ、馬鹿げた)説明があり、優れた使用例があります。

15
Alex Thornton

具体的に何が分からないのですか?ドキュメントには、次のことが説明されています。

ソースをコードまたはASTオブジェクトにコンパイルします。コードオブジェクトは exec ステートメントで実行するか、 の呼び出しで評価できますeval() 。sourceは、Unicode文字列、Latin-1でエンコードされた文字列、またはASTオブジェクトです。 ast ASTオブジェクトを操作する方法についてのモジュールのドキュメント。

したがって、pythonコードを受け取り、これらの2つのことを返します

  • execはpythonコードを実行します
  • evalは式を評価しますが、execよりも機能的ではありません
  • astを使用すると、コードが生成する Abstract Syntax Tree をナビゲートできます。
6