13.1 関数とは?

一般的な意味では関数とは引数(arguments)と呼ばれる与えられた入力値の計算を担うルールです。計算の結果は関数の値(value)、またはreturn値(return value)と呼ばれます。計算は変数の値やデータ構造の内容を変更する等の副作用をもつこともできます(Definition of side effectを参照)。純粋関数(pure function)とは、それらに加えて副作用をもたず、機種別やシステム状態のような外部要因とは無関係に同じ条件の引数にたいして常に同一の値をリターンする関数のことです。

ほとんどのコンピューター言語では、関数はそれぞれ名前をもちます。しかしLispでは厳密な意味において関数は名前をもちません。関数はオブジェクトであり、関数の名前の役割を果たすシンボルに関連づけることができますが(たとえばcar)、それはオプションです。関数の命名を参照してください。関数が名前を与えられたとき、通常はそのシンボルを“関数”として参照します(たとえば関数carのように参照する)。このマニュアルでは、関数名と関数オブジェクト自身との間の区別は通常は重要ではありませんが、それが意味をもつような場合には注記します。

スペシャルフォーム(special form)マクロ(macro)と呼ばれる関数likeなオブジェクトがいくつかあり、それらも引数を受け取って計算を行います。しかし以下で説明するようにEmacs Lispではこれらは関数とはみなされません。

以下は関数と関数likeなオブジェクトにたいする重要な条件です:

lambda expression

Lispで記述された関数(厳密には関数オブジェクト)。これらについては以降のセクションで説明します。 ラムダ式を参照のこと。

primitive

Lispから呼び出すことができるが実際にはCで記述されている。プリミティブはビルトイン関数(built-in functions)とかサブルーチン(subr)のようにも呼ばれる。それらの例には関数likeなcarappendが含まれる。加えてすべてのスペシャルフォーム(以下参照)もプリミティブとみなされる。

関数はLispの基礎となる部分(たとえばcar)であり、オペレーティングシステムのサービスにたいして低レベルのインターフェースを与え、高速に実行される必要があるために、通常はプリミティブとして実装されている。Lispで定義された関数と異なり、プリミティブの修正や追加には、Cソースの変更とEmacsのリコンパイルが必要となる。Emacsプリミティブの記述を参照のこと。

special form

プリミティブは関数と似ているが、すべての引数が通常の方法で評価されない。いくつかの引数だけが評価されるかもしれず、通常ではない順序で評価されるか、複数回評価されるかもしれない。プリミティブの例にはifandwhileが含まれる。スペシャルフォームを参照のこと。

macro

あるLisp式をオリジナルの式のかわりに評価される別の式に変換する、関数とは別のLispで定義された構文。マクロはスペシャルフォームが行う一連のことを、Lispプログラマーが行うのを可能にする。マクロを参照のこと。

command

プリミティブcommand-executeを通じて呼び出すことができるオブジェクトで、通常はそのコマンドにバインドされたキーシーケンスをユーザーがタイプすることにより呼び出される。インタラクティブな呼び出しを参照のこと。コマンドは通常は関数である。その関数がLispで記述されていれば、関数の定義内のinteractiveフォームによってコマンドとなる(コマンドの定義を参照)。関数であるコマンドは他の関数と同様、Lisp式から呼び出すこともできる。

キーボードマクロ(文字列かベクター)は関数ではないが、これらもコマンドである。キーボードマクロを参照のこと。シンボルの関数セルにコマンドが含まれてれば、わたしたちはそのシンボルをコマンドと言う(シンボルの構成要素を参照)。そのような名前つきコマンド(named command)M-xで呼び出すことができる。

closure

ラムダ式とよく似た関数オブジェクトだが、クロージャはレキシカル変数バインディングの環境にも囲われている。クロージャーを参照のこと。

byte-code function

バイトコンパイラーによりコンパイル済みの関数。クロージャ関数型を参照のこと。

autoload object

実際の関数のプレースホルダー。autoloadオブジェクトが呼び出されると、Emacsは実際の関数の定義を含むファイルをロードした後に実際の関数を呼び出す。autoloadを参照のこと。

関数functionpを使用して、あるオブジェクトが関数かどうかテストできます:

Function: functionp object

この関数はobjectが任意の種類の関数(funcallに渡すことができる)ならtをリターンする。functionpは関数を名づけるシンボルにたいしてはt、マクロやスペシャルフォームにたいしてはnilをリターンすることに注意。

objectは関数でなければ、この関数は通常はnilをリターンする。ただし関数オブジェクトの表現は複雑なので、効率上の理由によりobjectがたとえ関数でなくてもこの関数がtをリターンするときが稀にある。

任意の関数が期待する引数の個数を調べることもできます:

Function: func-arity function

この関数は指定されたfunctionの引数リストに関する情報を提供する。リターン値は(min . max)という形式のコンスセル。ここでminは引数の最小個数、maxは引数の最大個数、または&rest引数をもつ関数ではmanyfunctionがスペシャルフォームならシンボルunevalled

以下のようにある状況下ではこの関数は不正確な結果をリターンすることに注意:

functionpと異なり、以下の関数はシンボルをそれの関数定義としては扱いません

Function: subrp object

この関数はobjectがビルトイン関数(たとえばLispプリミティブ)ならtをリターンする。

(subrp 'message)            ; messageはシンボルであり、
     ⇒ nil                 ;   subrオブジェクトではない
(subrp (symbol-function 'message))
     ⇒ t
Function: byte-code-function-p object

この関数はobjectがバイトコード関数ならtをリターンする。たとえば:

(byte-code-function-p (symbol-function 'next-line))
     ⇒ t
Function: compiled-function-p object

この関数はobjectがELispソースコード形式ではなくても、何らかのマシンコードやバイトコードならtをリターンする。より正しくは、ビルドイン関数(別名“プリミティブ(primitive)”。関数とは?を参照)、バイトコンパイル済み関数(バイトコンパイルを参照)、ネイティブコンパイル済み関数(Lispからネイティブコードへのコンパイルを参照)、またはダイナミックモジュールからロードされた関数(Emacsのダイナミックモジュールを参照)の場合にtをリターンする。

Function: interpreted-function-p object

この関数はobjectがインタープリターによって解釈される関数ならtをリターンする。たとえば:

Function: closurep object

この関数はobjectがクロージャ(特殊な関数オブジェクト)ならtをリターンする。現在のところすべてのバイトコード関数、およびインタープリターに解釈されるすべての関数にたいしてクロージャが使用されている。

Function: subr-arity subr

これはfunc-arityと同様だがシンボルインダイレクションなしのビルトイン関数にたいしてのみ機能する。非ビルトイン関数にたいしてはエラーをシグナルする。かわりにfunc-arityの使用を推奨する。

Function: cl-functionp object

この関数はfunctionpと似ているが、リストとシンボルにたいしてnilリターンする点が異なる。

Function: primitive-function-p object

この関数はobjectがCで記述されたビルトインのプリミティブ(プリミティブ関数型を参照)であればtをリターンする。スペシャルフォームは関数ではないので、明確に除外されることに注意。スペシャルフォームも同じように認識したければ、subr-primitive-pを使うこと。


This page has generated for branch:work/emacs-30_69b16e5c63840479270d32f58daea923fe725b90, commit:5e3f74b56ff47b5bcef2526c70f53f749bbd45f6 to check Japanese translation.