Menu

PHPのアロー関数:fn() =>の書き方と例

アロー関数は、fn($x) => $x * 2と書く1つの式だけの無名関数です。外側の変数をuseなしで自動的に値渡しで使います。構文、キャプチャの仕組み、型、array_mapやusortのコールバック、通常のクロージャを使うべき場面を学びます。

このページのコードはエディタで実行できます - 編集してすぐに結果を確認できます。

アロー関数は短い無名関数です:fn($x) => $x * 2。=>のあとの本体は1つの式で、その値が返され、式が使う周りのコードの変数は自動的に値でキャプチャされます。アロー関数はPHP 7.4から使え、おもにコールバックとして使われます。

構文

fn、引数リスト、=>、1つの式の順に書きます。引数の型、デフォルト値、戻り値の型は通常の関数と同じように使えます。

returnキーワードも波括弧もありません。長い式も、読みやすさのために複数行に分けられます。

外側の変数は値でキャプチャされる

アロー関数は、作られたスコープのすべての変数を参照できます。その時点の値をコピーするので、中での変更は中にとどまり、関数を作ったあとの外での変更は見えません。

これが、変数を参照で共有できるfunction () use (&$count)との大きな違いです。アロー関数は外側の変数に再代入できません。ただし、キャプチャしたオブジェクトは変更できます(コピーは同じオブジェクトへのハンドルだからです)。また参照として宣言した引数は、どの関数とも同じように動きます:fn(array &$list) => $list[] = 'x'。

array_map、array_filter、usortのコールバック

ほとんどの配列関数はコールバックを受け取り、アロー関数がいちばん記述を減らしてくれるのはそこです。同じ絞り込みを両方の書き方で比べてみましょう。

<=>は-1、0、1を返し、これはusort()が求めるものそのものなので、フィールドでの並べ替えが1行に収まります。降順にするには$aと$bを入れ替えます。

アロー関数を返すアロー関数

キャプチャされる変数には外側のアロー関数の引数も含まれるので、ネストしてほかの値から関数を作れます。

array_filter()は元のキーを保つので、結果が添字1から始まっている点に注意してください。

fnとfunction:完全なクロージャが必要なとき

本体に複数の式が必要なときや、外側の変数を変更しなければならないとき、アロー関数は使えません。そのときは無名関数を使います。

fn($x) => ...function ($x) use ($y) { ... }
本体1つの式任意の文
戻り値自動明示的なreturn
外側の変数使ったものすべてを自動でuseに並べたものだけ
参照でキャプチャできないできる、use (&$y)
使えるようになった版PHP 7.4PHP 5.3

アロー関数が窮屈に感じるときは、たいていその処理が2つの処理であることを意味しています。上のように絞り込みと合計に分ければ、各コールバックを1つの式に保てます。

よくある質問

PHPのアロー関数とは何ですか?

PHP 7.4で導入された短い無名関数です:fn($x) => $x * 2。本体は1つの式で、その値が自動的に返され、use句なしで周りのスコープの変数を読めます。

PHPのアロー関数は複数行にできますか?

できません。=>のあとの本体は1つの式でなければならず、文を並べるブロックはありません。長い式を複数行に分けることはできますが、if、ループ、複数の文が必要なら、代わりにfunction () use (...) { ... }を使います。

アロー関数は外側の変数を変更できますか?

できません。アロー関数は外側の変数を値でキャプチャするので、fn() => $count++は自分のコピーを変えるだけで、外側の$countはそのままです。外側の変数を変更するには、use (&$count)を付けたクロージャを使います。

PHPのfnとfunctionの違いは何ですか?

fn($x) => ...は1つの式を持ち、それを暗黙に返し、使う外側の変数をすべて値でキャプチャします。function ($x) use ($y) { ... }はどんな文でも持て、明示的なreturnが必要で、useに並べた変数だけが見え、それらは参照でキャプチャすることもできます。

Coddyのプログラミング言語のイラスト

Coddyでコードを学ぼう

始める