ホームページ >バックエンド開発 >Python チュートリアル >Python でのクロージャの使用例
この記事では主に Python 基本チュートリアルでのクロージャの使い方に関する情報を紹介しますので、困っている方は
Python 基本チュートリアルでのクロージャの使い方
を参考にしていただければ幸いです。前書き:
クロージャは関数型プログラミングにおける重要な文法構造です。関数型プログラミングはプログラミング パラダイムです (手続き型プログラミングとオブジェクト指向プログラミングもプログラミング パラダイムです)。プロセス指向プログラミングでは関数を見てきましたが、オブジェクト指向プログラミングではオブジェクトを見てきました。関数とオブジェクトの基本的な目的は、コードを特定の論理的な方法で編成し、コードの再利用性を向上させることです。クロージャはコードを整理するための構造でもあり、コードの再利用性も向上します。 異なる言語は異なる方法でクロージャを実装します。 Python は関数オブジェクトに基づいており、クロージャの構文構造のサポートを提供します (Python がオブジェクトを使用して、特殊なメソッドやマルチパラダイムで特殊な構文を実装していることを何度も見てきました)。 Python ではすべてがオブジェクトであり、関数の文法構造もオブジェクトです。関数オブジェクトでは、関数オブジェクトの名前を変更したり、関数オブジェクトをパラメータとして渡したりするなど、通常のオブジェクトと同じように関数オブジェクトを使用します。 関数オブジェクトのスコープ
def line_conf(): def line(x): return 2*x+1 print(line(5)) # within the scope line_conf() print(line(5)) # out of the scopeline 関数は直線 (y = 2x + 1) を定義します。ご覧のとおり、line 関数は line_conf() で呼び出すことができますが、スコープ外で line を呼び出すと、既にスコープ外にあることを示す
NameError: name 'line' is not definedというエラーが発生します。 同様に、ラムダを使用して関数を定義する場合、関数オブジェクトのスコープはラムダが配置されているレベルと同じになります。
クロージャ
def line_conf(): def line(x): return 2*x+1 return line # return a function object my_line = line_conf() print(my_line(5))上記のコードは正常に実行できます。 line_confの戻り結果はlineオブジェクトに代入されます。上記のコードは 11 を出力します。 line() の定義で外部変数が参照された場合はどうなりますか?
def line_conf(): b = 15 def line(x): return 2*x+b return line # return a function object b = 5 my_line = line_conf() print(my_line(5))lineで定義された下位プログラムブロック内で上位変数bが参照されていることがわかりますが、bの情報はline定義の外に存在します(bの定義はlineの下位プログラムブロック内にありません)ライン)。 b を line の環境変数と呼びます。実際、line が line_conf の戻り値として使用される場合、line にはすでに b の値が含まれています (ただし、b は line に関連付けられていません)。 上記のコードは 25 を出力します。つまり、line で参照される b 値は、使用時の b 値ではなく、関数オブジェクトの定義時に参照できる b 値
です。 関数とその環境変数は一緒になって
クロージャを形成します。Python では、いわゆるクロージャは、環境変数の値を含む関数オブジェクトです。環境変数の値は、関数オブジェクトの __closure__ 属性に格納されます。たとえば、次のコード:
def line_conf(): b = 15 def line(x): return 2*x+b return line # return a function object b = 5 my_line = line_conf() print(my_line.__closure__) print(my_line.__closure__[0].cell_contents)
クロージャの実際的な例を見てみましょう:
def line_conf(a, b): def line(x): return ax + b return line line1 = line_conf(1, 1) line2 = line_conf(4, 5) print(line1(5), line2(5))
クロージャがない場合、直線関数を作成するたびに a、b、x を指定する必要があります。この方法では、より多くのパラメーターを渡す必要があり、コードの移植性が低下します。クロージャを使用して、実際に関数を作成します。線関数は広義の関数を定義します。この関数の一部の側面はすでに決定されています (直線である必要があります) が、他の側面 (a および b パラメーターなど) は未決定です。続いて、line_conf によって渡されたパラメータに基づいて、クロージャの形式で最終関数を決定します。
クロージャと並列操作
クロージャは、関数に定義する必要があるパラメータの数を効果的に減らします。これは並列操作に重要な意味を持ちます。並列コンピューティング環境では、各コンピューターに機能を担当させ、あるコンピューターの出力を次のコンピューターの入力と連結できます。最終的には、一連のコンピューター クラスターの一方の端からデータを入力し、もう一方の端からデータを出力する、組み立てラインのように作業します。この状況は、パラメーター入力が 1 つだけの関数に最適です。クロージャはこの目的を達成できます。
並列コンピューティングがホットスポットになりつつあります。これは、関数型プログラミングが再び人気を集めている重要な理由でもあります。関数型プログラミングは 1950 年代には存在していましたが、あまり広く使用されていませんでした。ただし、上で説明したパイプライン化された作業並列クラスタリング プロセスは、関数型プログラミングに完全に適しています。関数型プログラミングの自然な利点により、ますます多くの言語が関数型プログラミング パラダイムをサポートし始めています。
以上がPython でのクロージャの使用例の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。