PHPにおける配列:同種のデータをまとめて扱うためのしくみ

2015年2月25日(水)
野田 貴子

配列内の要素をまとめて処理する

配列を使う利点は、配列に入っている要素すべてに対して同じ処理ができることです。そのためには、配列をループして、すべての要素を1つずつ参照します。

for文のループ

数値配列の場合、前回取り上げたfor文のループを使うことができます。配列の長さは count 関数で求めることができます。

$myFamily  = array("チチ", "ハハ", "タロウ");
$length = count($myFamily);
for($i = 0; $i < $length; $i++) {
        echo "{$i}番目の名前は{$myFamily[$i]}です。\n";
}

// 0番目の名前はチチです。
// 1番目の名前はハハです。
// 2番目の名前はタロウです。

foreach文のループ

foreach文は、数値配列と連想配列のどちらにも使用できます。配列の長さを事前に求める必要はありません。

数値配列

$myFamily  = array("チチ", "ハハ", "タロウ");
foreach($myFamily as $key => $val) {
        echo "{$key}番目の名前は{$val}です。\n";
}

// 0番目の名前はチチです。
// 1番目の名前はハハです。
// 2番目の名前はタロウです。

$keyを使わない場合は、「foreach($myFamily as $val)」と省略して書くことができます。$val には $myFamily [$key] の値が入ります。例で使用した$keyや$valという変数名は任意に変更することができますので、分かりやすい名前を使うとよいでしょう。

連想配列

$myFamily = array(
    "father" => "チチ",
    "mother" => "ハハ",
    "me" => "タロウ"
);
foreach($myFamily as $relationship => $name) {
        echo "{$relationship}の名前は{$name}です。\n";
}

// fatherの名前はチチです。
// motherの名前はハハです。
// meの名前はタロウです。

ループ内で元の値を更新するとどうなるか

ループ中で値を参照しているだけ変数である$valなどを変更しても、元の配列には反映されません。

$myFamily  = array("チチ", "ハハ", "タロウ");
foreach($myFamily  as $val) {
        $val .= "ちゃん";
        echo "{$val}です。\n";
}

// チチちゃんです。
// ハハちゃんです。
// タロウちゃんです。

var_dump($myFamily);

// array(3) {
//   [0]=>
//   string(6) "チチ"
//   [1]=>
//   string(6) "ハハ"
//   [2]=>
//   string(9) "タロウ"
// }

元の配列を更新するためには、以下の例のようにループしている配列そのものの$myFamilyを更新します。

$myFamily  = array("チチ", "ハハ", "タロウ");
foreach($myFamily  as $key => $val) {
        $myFamily[$key] .= "ちゃん";
}
var_dump($myFamily);

// array(3) {
//   [0]=>
//   string(15) "チチちゃん"
//   [1]=>
//   string(15) "ハハちゃん"
//   [2]=>
//   string(18) "タロウちゃん"
// }

多重配列

配列の中には、さらに配列を入れることもできます。こうすることで、何段階でも配列の階層を深くすることができます。

$me = array(
        "name" => "タロウ",
        "age" => 50
);
$son = array(
        "name" => "ジロウ",
        "age" => 25
);
$daughter = array(
        "name" => "ハナコ",
        "age" => 20
);
$me["children"] = array($son, $daughter);

var_dump($me);
// array(3) {
//   ["name"]=>
//   string(9) "タロウ"
//   ["age"]=>
//   int(50)
//   ["children"]=>
//   array(2) {
//     [0]=>
//     array(2) {
//       ["name"]=>
//       string(9) "ジロウ"
//       ["age"]=>
//       int(25)
//     }
//     [1]=>
//     array(2) {
//       ["name"]=>
//       string(9) "ハナコ"
//       ["age"]=>
//       int(20)
//     }
//   }
// }

多重配列内のデータを扱うためには、for文やforeach文などのループ文も多重にします。

foreach($me as $key => $val) {
    echo "{$key} は {$val} です。\n";
    if ($key === "children") {
        foreach($val as $ckey => $cval) {
            echo "{$ckey} 人目の子供の名前は {$cval['name']} です。\n";
        }
    }
}

// name は タロウ です。
// age は 50 です。
// children は Array です。
//(配列を echo すると「Array」が出力されます)
// 0 人目の子供の名前は ジロウ です。
// 1 人目の子供の名前は ハナコ です。

文字列から配列に変換する

文字列を配列に変換する用途は、たくさんあります。例えばURLのパラメータで指定されたカンマ区切りのカテゴリーID(&cat="a,b,c" の "a,b,c" の部分など)を、配列に入れると array("a", "b", "c") のようになり、プログラムで扱いやすくなります。文字列全体を配列の1つの要素に変換するためには、その文字列を「array(」と「)」で囲います。

$string = "あかんぼあかいなあいうえお";
$array = array($string);

var_dump($array);
// array(1) {
//   [0]=>
//   string(39) "あかんぼあかいなあいうえお"
// }

文字列を区切り文字で区切って配列に変換するためには、explode関数を使います。第一引数(",")に区切り文字を、第二引数には分割したい文字列($colors)を指定します。

$colors = "赤,青,緑";
$arColors = explode(",", $colors);

var_dump($arColors);
// array(3) {
//   [0]=>
//   string(3) "赤"
//   [1]=>
//   string(3) "青"
//   [2]=>
//   string(3) "緑"
// }

foreach($arColors as $val) {
        // 配列になったのでループもできます
}

explode 関数には第三引数もあり、いろいろな分割方法を指定できます。以下に例を挙げますが、詳しくはドキュメントを参照してください。

// 第三引数に正数を指定すると、その個数に分割されます
$phone = "03-1234-5678";
var_dump(explode("-", $phone, 2));
// array(2) {
//   [0]=>
//   string(2) "03"
//   [1]=>
//   string(9) "1234-5678"
// }
// 第三引数に負数を指定すると、引数を正数にした個数の要素が最後から切り捨てられます
$filename = "example.tmp.exe";
var_dump(explode(".", $filename, -1));
// array(2) {
//   [0]=>
//   string(7) "example"
//   [1]=>
//   string(3) "tmp"
// }

配列から文字列に変換する

今度は逆に配列から文字列に変換する方法です。配列で処理をした後に、URLのパラメータに書き出したり、ファイルに出力したりするのに使えます。こちらはimplode関数を使います。

$arParams = array("year=2014", "month=12", "day=25");
$params = implode("&", $arParams);

var_dump($params);
// string(25) "year=2014&month=12&day=25"

その他の配列操作関数

上記で紹介した以外にも配列を操作する関数は山ほどありますので、「こういう処理をしたいな」と思ったら、とりあえずドキュメントを調べてみるとよいでしょう。以下はほんの一例です。

array_key_exists

配列の中に指定したキーが存在するかどうかを調べます。キーの有無によって、その後の処理を変えたい場合に使います。

if (array_key_exists("father", $arFamily)) {
        // $arFamily["father"] があるならtrue
}

in_array

ある値が、配列の中にあるあるかどうかを調べます。

if (in_array("味噌汁", $arDinner)) {
        // $arDinner[キーは不問] == "味噌汁" ならtrue
}

「in_array("味噌汁", $arDinner, true)」のように第三引数に「true」を指定すると、「==」 ではなく「===」での判定になります。

array_search

配列の中に指定した値があれば、対応するキーを返します。複数の要素にヒットした場合は、最初に見つかったものを返します。第三引数は型の等しさもチェックするかどうかで、デフォルトではOFF(false)になっています。

$arScores = array(
        "チチ" => 120,
        "ハハ" => 120,
        "タロウ" => "120"
);
var_dump(array_search("120", $arScores));
// string(6) "チチ"
var_dump(array_search("120", $arScores, true));
// string(9) "タロウ"
var_dump(array_search("100", $arScores));
// bool(false)

配列のソート関数

配列内の要素を並び替える関数もたくさんあります。それぞれ特徴がありますので、ソート関数の比較や各ソート関数のドキュメントを読んでみてください。普通にソートすると数値順やアルファベット順になりますが、自作の関数を使って特殊な並び順でソートすることもできます。例えば住所による五十音順ではないソート(XYZ区はABC区よりも前、など)ができます。

sort普通にソートする
rsort逆順にソートする
ksortキーでソートする
krsortキーで逆順にソートする
asort連想キーと要素との関係を維持しつつソートする
arsort連想キーと要素との関係を維持しつつ逆順にソートする
usortユーザー定義の比較関数を使用して、値でソートする
uksortユーザー定義の比較関数を用いて、キーでソートする
uasortユーザー定義の比較関数でソートし、連想インデックスを保持する

おわりに

いかがでしたか? 覚えることがたくさんありそうですが、PHPでは配列を使わないプログラムはないくらいに配列をよく利用しますので、きっとすぐに慣れると思いますよ。それではまた。

1983年生まれ。大学卒業後、ソフトウェア開発の営業を経て、ソフトウェア開発業務に転向。現在は自社パッケージのフロントエンド開発のほか、PHPでの受託開発案件、日→英のローカライズ案件などを担当。

連載バックナンバー

Think ITメルマガ会員登録受付中

Think ITでは、技術情報が詰まったメールマガジン「Think IT Weekly」の配信サービスを提供しています。メルマガ会員登録を済ませれば、メルマガだけでなく、さまざまな限定特典を入手できるようになります。

Think ITメルマガ会員のサービス内容を見る

他にもこの記事が読まれています