クロージャ
クロージャ（クロージャー、）、関数閉包はプログラミング言語における関数オブジェクトの一種。いくつかの言語ではラムダ式や無名関数で実現している。引数以外の変数を実行時の環境ではなく、自身が定義された環境（静的スコープ）において解決することを特徴とする。関数とそれを評価する環境のペアであるともいえる。この概念は少なくとも1960年代のSECDマシンまで遡ることができる。まれに、関数ではなくとも、環境に紐付けられたデータ構造のことをクロージャと呼ぶ場合もある。クロージャをサポートした言語のコーディングでは、関数の中に関数を定義することができる。その際に、外側の関数で宣言された変数を内側の関数で操作することができる。主な利点としてはグローバル変数の削減が挙げられる。
典型的にはクロージャは、外側の関数（以下、エンクロージャ）の内側の関数リテラルや、ネストした関数定義によって必要になる。言語により、そのような内側の関数内に出現する自由変数（内側の関数の仮引数でもなく、内側の関数自身のローカル変数でもない変数）の扱いは異なるが、自由変数が、その呼び出しにおけるエンクロージャのその名前の変数を、レキシカルに参照するのがクロージャであり、実行時に外部の関数が実行された際、クロージャが形成される。クロージャは内部の関数のコードとエンクロージャのスコープ内の必要なすべての変数への参照からなる。
クロージャはプログラム内で環境を共有するための仕組みである。レキシカル変数はグローバルな名前空間を占有しないという点でグローバル変数とは異なっている。またオブジェクトのインスタンス変数とは、オブジェクトのインスタンスではなく関数の呼び出しに束縛されているという点で異なる。
クロージャは関数型言語では遅延評価やカプセル化のために、また高階関数の引数として広く用いられる。
例： クロージャを使ったカウンタの例を で示す。
関数 codice_1 の中でクロージャが使用されている。codice_2 に代入された無名関数は codice_1 内のローカル変数 codice_4 を参照している。codice_2 を呼び出すたびに codice_4 はインクリメントされていく。
クロージャには多くの用途がある。Schemeは完全な静的スコープのクロージャを持つ最初の言語として登場した。Common Lispはそれを取り入れた。実質的にすべての関数型言語（Scala、Haskell、OCamlなど）とSmalltalkに由来するオブジェクト指向言語は何らかの形でクロージャを持っている。
クラスを使用するオブジェクト指向言語では、メソッドの中でクラス定義できることが、完全なクロージャになるには必要だが、メソッド・関数の中でラムダ式・無名関数が使え、その中から外のローカル変数を読み書きできれば、一般的にはそのプログラミング言語はクロージャを使えると呼ばれる。よって、ラムダ式・無名関数を含めると、クロージャを持つ言語に、C# 3.0、C++11、ECMAScript（JavaScriptを含む）、Groovy、Java (8以降)、Perl、Python、Ruby、PHP（5.3以降）、Lua、Squirrelなどがある。
セマンティクスはそれぞれ大きく異なっているが、多くの現代的な汎用のプログラミング言語は静的スコープとクロージャのいくつかのバリエーションを持っている。
言語ごとにスコープのセマンティクスが異なるように、クロージャの定義も異なっている。汎用的な定義では、クロージャが捕捉する「環境」とは、あるスコープのすべての変数の束縛の集合である。しかし、この変数の束縛というものの意味も言語ごとに異なっている。命令型言語では、変数は値を格納するためのメモリ中の位置と束縛される。この束縛は変化せず、束縛された位置にある値が変化する。クロージャは束縛を捕捉しているので、そのような言語での変数への操作は、それがクロージャからであってもなくとも、同一のメモリ領域に対して実行される。例として、ECMAScriptを取り上げると
関数 codice_7 と2つのクロージャがローカル変数 codice_8 に束縛された同一のメモリ領域を使用していることに注意。
一方、多くの関数型言語、例えばML、は変数を直接、値に束縛する。この場合、一度束縛された変数の値を変える方法はないので、クロージャ間で状態を共有する必要はない。単に同じ値を使うだけである。
さらに、Haskellや、Common Lisp上に作られたCLAZYパッケージ(言語拡張)など、遅延評価を行う関数型言語では、変数は将来の計算結果に束縛される。例を挙げる。
codice_9 は計算 codice_10 に束縛されており、この場合は0による除算である。しかしながら、クロージャが参照しているのはその値ではなく計算であるので、エラーはクロージャが実行され、実際にその束縛を使おうと試みたときに現れる。
さらなる違いは静的スコープである制御構文、C風の言語における codice_11・codice_12・codice_13 などにおいて現れる。ECMAScriptなどの言語では、これらはクロージャ毎に束縛され、構文上の束縛を隠蔽する。つまり、クロージャ内からの codice_14 はクロージャを呼び出したコードに制御を渡す。しかしSmalltalkでは、このような動作はトップレベルでしか起こらず、クロージャに捕捉される。例を示して、この違いを明らかにする。
Smalltalkにおける codice_15 はECMAScriptにおける codice_14 にあたるものだと頭に入れれば、一目見た限りではどちらのコードも同じことをするように見える。違いは、ECMAScriptの例では codice_14 はクロージャを抜けるが関数 codice_7 は抜けず、Smalltalkの例では codice_15 はクロージャだけではなくメソッド codice_7 をも抜ける、という点である。後者の特徴はより高い表現力をもたらす。Smalltalkの codice_21 は通常のメソッドであり、自然に制御構文が定義できている。一方、ECMAScriptでは codice_14 の意味が変わってしまうので、同じ目的には codice_23 という新しい構文を導入しなければならない。
しかし、スコープを越えて生存する継続には問題もある。
上の例でメソッド codice_7 が返すブロックが実行されたとき、codice_7 から値を返そうとする。しかし、codice_7 の呼び出しは既に完了しているので、この操作はエラーとなる。
Rubyなどの言語では、プログラマが codice_14 の振る舞いを選ぶことができる。
この例の codice_28 と codice_29 はどちらもクロージャを作るための方法である。しかし、それぞれが作ったクロージャの codice_14 の振る舞いに関しては、異なるセマンティクスを持っている。
Common Lispにおいては、すべての関数、クロージャ、無名関数などは最終的にアセンブリ言語に似たtagbodyに展開されると考えてよい。原理的にはすべてのプログラムは機械語へコンパイルまたはインタープリットされるはずなので、他の言語においてもこの発想は自然である。tagbodyは内部でgo命令によってタグにジャンプすることができる。これも、直接的にアセンブリのラベル及びJMP命令と対応させられる。
関数はタグ(名前)付きのブロックであり、クロージャ、無名関数などは無名のブロックをもつ。無名ブロックの名前はnilとなる。この仕様の下で、Common Lispにはreturnおよびreturn-fromが用意されている。(return 0)は(return-from nil 0)と同値であり、すなわち一番近いブロックから抜け出すことを意味する。従って、どのような状況下でも、ブロックの名前を指定して任意の場所から脱出することができる。以下に例を示す。
最新規格であるC++11では、ラムダ式が使え、以下の2つの方法でローカル変数のキャプチャをサポートする。詳細はC++11を参照。
C言語では、コールバックをサポートするライブラリの中に、2つの値を利用したコールバックを行うものがある。関数ポインタと任意のデータを指す codice_31 ポインタである。ライブラリがコールバック関数を実行するたび、データポインタを使用する。これによってコールバックは状態を管理することができ、登録した情報を参照できる。このイディオムはクロージャと機能面で似ているが、構文面では似ていない。
古いC++（C++11よりも前）では、codice_32 をオーバーロードすることで、関数オブジェクトが利用できる。これは関数型言語における関数にいくらか似た振る舞いをみせる。関数オブジェクトは実行時に作ることができ、状態を持つこともできる。しかし、クロージャのように自動的にローカル変数を捕捉するようなことはしない。
また、Java の無名クラスに相当するローカルクラスを使用し、関数内でクラスを定義することも可能だが、Java の無名クラス以上に制約条件が多く、参照できる外のローカル変数は static 変数のみ。
Eiffelにはクロージャを定義するためのinline agent（インラインエージェント）がある。インラインエージェントはルーチンを表すオブジェクトで、次のように利用する。
codice_33 の実引数はインラインエージェントで、2つの引数を持つ手続きである。ユーザがこのボタンをクリックして、codice_34 タイプのイベントが起こると、マウスの座標を引数としてこの手続きが実行される。
Eiffelのインラインエージェントの大きな限界は、外側のスコープのローカル変数を参照できないという点である。
Java 7 以前では、メソッド内部に「無名クラス」を定義することで似たようなことができる。無名クラスからは、そのメソッドの codice_35 （リードオンリー）なローカル変数を、無名クラスのメンバ変数と名前が被らない限り、参照できる。
要素が1つの配列を codice_35 な参照で保持すれば、クロージャで1つのローカル変数を参照する機能をエミュレートできる。内部クラスはその参照の値そのものを変えることはできないが、参照されている配列の要素の値は変えることができるからである。このテクニックはJavaに限ったものではなく、Pythonなど似た制限を持つ言語でも有効である。
Javaに完全なクロージャを追加するという言語拡張が検討されていた。様々な問題により、クロージャを導入せずに、SAM Typeなインターフェース実装の簡単な表記法が Java 8 にて導入された。
クロージャは典型的には関数コードへのポインタ及び関数の作成時の環境の表現（例えば、使用可能な変数とその値の集合など）を含む特別なデータ構造によって実装される。
ある言語処理系の実行時のメモリモデルがすべてのローカル変数を線形なスタックに確保するものであれば、クロージャを完璧に実装するのは容易ではない。それは、以下のような理由による。
第1の問題を解決するために、クロージャを実装するプログラミング言語は大抵、ガベージコレクションを備えている。この場合、クロージャへの参照が全て無効になった時に、レキシカル変数はガベージコレクタに渡される。
第2の問題を解決するためには、デリゲートのように、関数の参照と実行環境の参照をセットで扱える必要がある。しかし、これではC言語のようなネイティブコードの関数の呼び出しとの互換性がなくなる。そのため、実行時にスタックやヒープに、エンクロージャのスタックポインタを埋め込んだ、実際の関数を起動するだけの小さな関数（トランポリン関数）を動的に生成することでも実装できる。しかし、セキュリティの観点から近代的なOSでは標準でスタックやヒープ上のコードの実行を禁止しているのが一般的であり、この制限を一時的・部分的に解除することをサポートしている環境でなければ実現できない。
現代的なScheme処理系は、クロージャに使用される可能性のあるローカル変数は動的に確保し、そうでないものはスタックに確保するなどの最適化を行うものが多い。