Foreach文
foreach文(フォーイーチぶん)とはプログラミング言語においてリストやハッシュテーブルなどのデータ構造の各要素に対して与えられた文の実行を繰り返すというループを記述するための文である。foreach文はしばしばfor文の一部という位置付けにある。for文と異なり要素の参照順序が定義されないこともある。
目次
処理の流れ
基本的な構文 (Perl) は以下のようになる。
foreach 変数 (リスト) {
文
}
このループはだいたい次のような手順で実行される。
- 変数にリストの中のある要素への参照を代入する。
- 文を実行する。
- リストの全要素を参照し終わっていない場合は、変数に未参照の要素を代入して文の実行へ戻る。
ここで、線形リストや配列など要素の順序が決まっているものは、通常その順序でループが実行されるので、この場合以下とほぼ同様である。
for ( my $i = 0; $i < @list; $i++ ) {
変数 = $list[$i];
文
}
ただし、ハッシュテーブル(連想配列)については要素の順序関係が決定できないこともあるため、一般に参照順序は不定である。
文法
awk
awkにおいても連想配列の処理を可能にしている。
for(変数 in 配列) { 文 }
C#
foreach (変数 in 配列) { 文 }
配列のほか、IEnumeratorもしくはIEnumerator<T>を実装したオブジェクトでもよい。
C++
C++は、2011年での規格改定(通称C++11)にて、範囲ベースの for ループが言語仕様として追加されている。
for (変数 : 配列)
{
文
}
上記で配列と記した箇所には、配列のほか、std::vectorやstd::arrayのような標準ライブラリにおいてコンテナに分類される各種のオブジェクトなども使用できる。
そのほか、1998年の標準規格化当初からC++標準ライブラリにfor_eachアルゴリズム(関数テンプレート)が存在する。
関数オブジェクト = std::for_each(
先頭イテレータ,
末尾イテレータ,
関数オブジェクト
);
C++11では、C#同様に型推論およびラムダ式を組み合わせることで、上記の構文が威力を発揮するようになる。
また、C++/CLI言語およびMicrosoft Visual C++ 2005以降の独自拡張機能では、for each
文を使用できるが、不安定で正常に動作しない場合がある。ただしこれはC++11における範囲ベース for ループとは互換性を持たない。
D
式を評価し、その結果は静的配列、動的配列、連想配列、構造体、クラスでなければいけない。式部分が配列である場合は変数は複数宣言する事が出来る。
foreach(変数 ; 式) { 文 }
Java 5.0以降
拡張For文などと呼び、Java 5.0 で導入された。For文の特殊なものとして捉えられるが、Foreach文に相当する。
for(変数 : リスト等) { 文 }
JavaScript, ActionScript
オブジェクトの反復処理にはfor-in文を用いる。変数にはプロパティ名(連想配列で言うキー)が代入されるので、プロパティの値は式 オブジェクト[変数]
で取得する。
for ( var 変数 in オブジェクト ) {
文
}
JavaScriptのfor-in文は、ユーザー定義のプロパティについて、プロトタイプチェーンをさかのぼって反復処理を行う。このため、特に配列に対してfor-in文を用いると、他の言語とは異なる挙動をすることがある。
var array = new Array(3);
var output = "";
for (var key in array) { output += key + " "; }
// このとき array.length === 3 であるが、
// array にユーザー側からプロパティ(配列要素)を定義していないので、
// output === "" である。
// 配列もオブジェクトなので、数値以外のプロパティを設定できる。
array.foo = "foo"
output = "";
for (var key in array) { output += key + " "; }
// このとき output === "foo " である。
// オブジェクトに新しいインスタンスメソッドを追加してみる。
Object.prototype.myMethod = function () {};
output = "";
for (var key in array) { output += key + " "; }
// 配列もオブジェクトなので、このとき output === "foo myMethod " である。
// なおもちろん、この時点でも array.length === 3 である。
ECMA-262第5版 (JavaScript 1.6, ActionScript 3.0) からは、ArrayインスタンスにforEachメソッドが追加された。
array.forEach(function (変数) {
文
});
ECMA-262第5版からは、オブジェクトの値で反復処理をするfor each-in文も導入された(スペースで分けられていることに注意)。
for each ( 変数 in オブジェクト ) {
文
}
Perl
しばしばforが代用とされる。Perlにおいて、forとforeachは同義語である。
foreach 変数 (リスト等) { 文 }
PHP
foreach (配列 as 変数) { 文 }
foreach (配列 as 変数1 => 変数2) { 文 }
前者の場合、処理手順は他の言語と同様だが、後者の場合、変数1に配列の添字が、変数2に要素が代入される。
Python
PythonにおけるFor文とは、他の言語におけるForeach文と同等である。
for 変数 in リスト等 : 文
Ruby
for 変数 in リスト等 文 end
これは以下のイテレータ構文と等価である。
リスト等.each do |変数| 文 end
なお、Rubyに関してはもっぱら後者の構文が好まれる傾向にある。
Visual Basic
For Each 変数 In リスト等 文 Next 変数
Windows PowerShell
foreach (変数 in リスト等) { 文 }
HSP
foreach 変数 文 loop
なでしこ
(リスト)を反復。 文
変数は「それ」に代入される。
シェルスクリプト
cshではforeachと書き、shではforと書く。実用上リストの部分にはワイルドカードを含むファイル列を書くことが多い。
csh系
foreach 変数 ( リスト ) 文 end
sh系
for 変数 in リスト do 文 done
番外編
PL/SQL
OracleのPL/SQLにも、カーソルというForEachと似たような機能が実装されている。 カーソルは用途が限定されているため、番外編として紹介する。
SELECT文でとってきた複数レコードを、カーソルを使って順繰り出力するPL/SQL文を示す。
DECLARE CURSOR C IS SELECT * FROM TBL1 WHERE TBL1.FIELD1 >= 100; BEGIN FOR D IN C LOOP DBMS_OUTPUT.PUT_LINE(D.FIELD1 || ' ' || D.FIELD2 || ' ' || D.FIELD3); END LOOP; END;