PHPでは、配列のキーに文字列を指定したものを連想配列と呼びます。
例えば、次のような配列です。
$user = [
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
'age' => 28,
];
通常の配列では 0、1、2 のような数値インデックスで値を管理しますが、連想配列では 'name' や 'email' のようなキーを使って値を管理します。
echo $user['name'];
// Tanaka
PHPで連想配列を検索する場合、主に次のような処理を行います。
// キーが存在するか調べる
array_key_exists('email', $user);
// 値が存在するか調べる
in_array('Tanaka', $user, true);
// 値からキーを取得する
array_search('Tanaka', $user, true);
// 条件に合う要素を抽出する
array_filter($users, fn($user) => $user['age'] >= 20);
連想配列の検索では、「キーを探したいのか」「値を探したいのか」「条件に合う要素を取り出したいのか」によって使う関数が変わります。
そのため、まずは目的別に使い分けを理解することが大切です。
PHPの連想配列検索でよく使う関数
連想配列の検索でよく使う関数は、主に次のとおりです。
| 目的 | 使用する関数 |
|---|---|
| キーが存在するか調べる | array_key_exists() |
キーが存在し、値が null でないか調べる | isset() |
| 値が存在するか調べる | in_array() |
| 値からキーを取得する | array_search() |
| 条件に合う要素を抽出する | array_filter() |
| 特定の列だけを取り出す | array_column() |
| 値をキーに変換して検索しやすくする | array_flip() |
| 条件に合う最初の値を取得する | array_find() |
| 条件に合う最初のキーを取得する | array_find_key() |
ただし、array_find() や array_find_key() はPHP 8.4以降で使える関数です。
PHP 8.3以前の環境では使えないため、古い環境も考慮する場合は foreach を使った検索方法も覚えておくとよいでしょう。
キーが存在するか検索する方法
array_key_exists() を使う
連想配列で、特定のキーが存在するか調べたい場合は array_key_exists() を使います。
$user = [
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
];
if (array_key_exists('email', $user)) {
echo 'emailキーは存在します';
} else {
echo 'emailキーは存在しません';
}
実行結果は次のようになります。
emailキーは存在します
array_key_exists() は、指定したキーが配列に存在するかを調べる関数です。
連想配列で「その項目があるかどうか」を確認したい場合によく使います。
値が null でもキーの存在を判定できる
array_key_exists() の大きな特徴は、値が null でもキーが存在すれば true を返すことです。
$user = [
'name' => 'Tanaka',
'email' => null,
];
var_dump(array_key_exists('email', $user));
実行結果は次のとおりです。
bool(true)
email の値は null ですが、email というキー自体は存在しています。
そのため、array_key_exists() は true を返します。
これは、フォーム入力やAPIレスポンスなどで「値が空かどうか」ではなく、「項目自体が存在するか」を確認したい場合に便利です。
array_key_exists() が向いているケース
array_key_exists() は、次のようなケースに向いています。
$config = [
'debug' => true,
'cache' => false,
'timezone' => 'Asia/Tokyo',
];
if (array_key_exists('cache', $config)) {
echo 'cache設定があります';
}
この例では、cache の値は false です。
しかし、cache というキーは存在しているため、array_key_exists() では true になります。
設定配列では、false や null に意味がある場合もあります。
そのような場合は、値の真偽ではなく、キーの存在を確認できる array_key_exists() が適しています。
isset() でキーの存在を確認する方法
isset() の基本的な使い方
isset() でも、連想配列のキーが存在するかを確認できます。
$user = [
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
];
if (isset($user['email'])) {
echo 'emailは設定されています';
}
実行結果は次のとおりです。
emailは設定されています
isset() は、指定した変数や配列の要素が存在し、なおかつ値が null ではない場合に true を返します。
isset() は null の場合に false になる
isset() を使うときに注意したいのは、値が null の場合です。
$user = [
'name' => 'Tanaka',
'email' => null,
];
var_dump(isset($user['email']));
var_dump(array_key_exists('email', $user));
実行結果は次のようになります。
bool(false)
bool(true)
email キーは存在しています。
しかし、値が null のため、isset() は false を返します。
一方、array_key_exists() はキーの存在だけを見るため、true を返します。
array_key_exists() と isset() の違い
array_key_exists() と isset() の違いは、次のように整理できます。
| 状態 | array_key_exists() | isset() |
|---|---|---|
| キーがあり、値もある | true | true |
キーがあり、値が null | true | false |
| キーがない | false | false |
つまり、キーの存在だけを確認したい場合は array_key_exists()、値が null ではないことも確認したい場合は isset() を使います。
// キーが存在するか確認したい
array_key_exists('email', $user);
// キーが存在し、値がnullではないか確認したい
isset($user['email']);
この違いは、PHPの連想配列検索で特に重要です。
値が存在するか検索する方法
in_array() を使う
連想配列の中に特定の値が存在するか調べる場合は、in_array() を使います。
$user = [
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
];
if (in_array('Tanaka', $user, true)) {
echo 'Tanakaは存在します';
}
実行結果は次のとおりです。
Tanakaは存在します
in_array() は、配列の中に指定した値があるかどうかを調べる関数です。
連想配列でも通常の配列と同じように使用できます。
第3引数には true を指定する
in_array() を使うときは、第3引数に true を指定するのがおすすめです。
in_array(検索する値, 配列, 厳密比較するか);
第3引数を true にすると、値だけでなく型も含めて比較します。
例えば、次のコードを見てください。
$data = [
'code' => '1',
];
var_dump(in_array(1, $data));
var_dump(in_array(1, $data, true));
実行結果は次のようになります。
bool(true)
bool(false)
第3引数を省略した場合、文字列の '1' と整数の 1 が同じように扱われることがあります。
一方、第3引数に true を指定すると、文字列 '1' と整数 1 は別の値として扱われます。
そのため、実務では次のように書くのが安全です。
in_array($value, $array, true);
特に、ID、ステータスコード、数値文字列などを扱う場合は、型の違いによる誤判定を防ぐために厳密比較を使いましょう。
値からキーを検索する方法
array_search() を使う
値を検索して、その値に対応するキーを取得したい場合は array_search() を使います。
$user = [
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
];
$key = array_search('Tanaka', $user, true);
echo $key;
実行結果は次のとおりです。
name
'Tanaka' という値は 'name' キーに入っているため、array_search() は name を返します。
array_search() の戻り値に注意する
array_search() は、値が見つかった場合は対応するキーを返します。
見つからなかった場合は false を返します。
$user = [
'id' => 1,
'name' => 'Tanaka',
];
$key = array_search('Suzuki', $user, true);
var_dump($key);
実行結果は次のとおりです。
bool(false)
ここで注意したいのは、キーが 0 の場合です。
$data = [
0 => 'apple',
1 => 'banana',
];
$key = array_search('apple', $data, true);
if ($key) {
echo '見つかりました';
} else {
echo '見つかりませんでした';
}
実行結果は次のようになります。
見つかりませんでした
apple は見つかっています。
しかし、返ってきたキーが 0 のため、if ($key) では false と判定されてしまいます。
そのため、array_search() の結果を判定するときは、必ず !== false を使います。
$key = array_search('apple', $data, true);
if ($key !== false) {
echo '見つかりました。キーは ' . $key . ' です';
} else {
echo '見つかりませんでした';
}
実行結果は次のとおりです。
見つかりました。キーは 0 です
array_search() を使うときは、次の書き方を基本にしましょう。
$key = array_search($value, $array, true);
if ($key !== false) {
// 見つかった場合の処理
}
条件に合う要素を検索する方法
array_filter() を使う
単純に値が一致するかどうかではなく、条件に合う要素を抽出したい場合は array_filter() を使います。
例えば、年齢が20歳以上のユーザーだけを取り出す場合は、次のように書けます。
$users = [
'user1' => ['name' => 'Tanaka', 'age' => 28],
'user2' => ['name' => 'Suzuki', 'age' => 35],
'user3' => ['name' => 'Sato', 'age' => 19],
];
$adults = array_filter($users, function ($user) {
return $user['age'] >= 20;
});
print_r($adults);
実行結果は次のとおりです。
Array
(
[user1] => Array
(
[name] => Tanaka
[age] => 28
)
[user2] => Array
(
[name] => Suzuki
[age] => 35
)
)
array_filter() は、配列の各要素をコールバック関数に渡し、戻り値が true になった要素だけを残します。
array_filter() はキーを保持する
array_filter() を使うと、元のキーが保持されます。
$numbers = [
10 => 'A',
20 => 'B',
30 => 'C',
];
$result = array_filter($numbers, function ($value) {
return $value !== 'B';
});
print_r($result);
実行結果は次のとおりです。
Array
(
[10] => A
[30] => C
)
キーは 0、1 のように振り直されません。
元の 10 と 30 がそのまま残ります。
通常の配列でも同じです。
$numbers = [10, 20, 30, 40];
$result = array_filter($numbers, function ($number) {
return $number >= 30;
});
print_r($result);
実行結果は次のようになります。
Array
(
[2] => 30
[3] => 40
)
このように、条件に合う要素だけを残した結果、キーが飛び飛びになることがあります。
キーを振り直す場合は array_values() を使う
array_filter() の結果を連番の配列にしたい場合は、array_values() を使います。
$numbers = [10, 20, 30, 40];
$result = array_filter($numbers, function ($number) {
return $number >= 30;
});
$result = array_values($result);
print_r($result);
実行結果は次のとおりです。
Array
(
[0] => 30
[1] => 40
)
APIレスポンスとしてJSONを返す場合は、この違いが特に重要です。
$numbers = [10, 20, 30, 40];
$result = array_filter($numbers, function ($number) {
return $number >= 30;
});
echo json_encode($result);
実行結果は次のようになる場合があります。
{"2":30,"3":40}
キーが連番でないため、JSONでは配列ではなくオブジェクトのような形になります。
配列として返したい場合は、array_values() でキーを振り直します。
$result = array_values($result);
echo json_encode($result);
実行結果は次のようになります。
[30,40]
キーと値の両方を使って検索する方法
ARRAY_FILTER_USE_BOTH を使う
array_filter() では、値だけでなくキーも使って検索できます。
キーと値の両方を使いたい場合は、ARRAY_FILTER_USE_BOTH を指定します。
$data = [
'apple' => 120,
'banana' => 80,
'orange' => 100,
];
$result = array_filter(
$data,
function ($value, $key) {
return $value >= 100 && str_contains($key, 'a');
},
ARRAY_FILTER_USE_BOTH
);
print_r($result);
実行結果は次のとおりです。
Array
(
[apple] => 120
[orange] => 100
)
この例では、次の2つの条件を満たす要素を取り出しています。
値が100以上
かつ
キーに a が含まれる
ARRAY_FILTER_USE_BOTH を指定すると、コールバック関数に値とキーの両方が渡されます。
キーだけを使って検索する場合は ARRAY_FILTER_USE_KEY を使う
キーだけを条件にして検索したい場合は、ARRAY_FILTER_USE_KEY を使います。
$data = [
'user_name' => 'Tanaka',
'user_email' => 'tanaka@example.com',
'admin_name' => 'Suzuki',
];
$result = array_filter(
$data,
function ($key) {
return str_starts_with($key, 'user_');
},
ARRAY_FILTER_USE_KEY
);
print_r($result);
実行結果は次のとおりです。
Array
(
[user_name] => Tanaka
[user_email] => tanaka@example.com
)
この例では、キーが user_ で始まる要素だけを抽出しています。
Webマーケティングやアクセス解析の処理では、次のように utm_ で始まるパラメータだけを取り出したいケースがあります。
$params = [
'utm_source' => 'google',
'utm_medium' => 'cpc',
'utm_campaign' => 'summer_sale',
'page' => 3,
'sort' => 'new',
];
$utmParams = array_filter(
$params,
function ($key) {
return str_starts_with($key, 'utm_');
},
ARRAY_FILTER_USE_KEY
);
print_r($utmParams);
実行結果は次のようになります。
Array
(
[utm_source] => google
[utm_medium] => cpc
[utm_campaign] => summer_sale
)
多次元連想配列から検索する方法
多次元連想配列の例
実務では、次のような多次元配列を検索することが多いです。
$users = [
[
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
'role' => 'admin',
],
[
'id' => 2,
'name' => 'Suzuki',
'email' => 'suzuki@example.com',
'role' => 'editor',
],
[
'id' => 3,
'name' => 'Sato',
'email' => 'sato@example.com',
'role' => 'editor',
],
];
このような配列から、特定のIDを持つユーザーや、特定の役割を持つユーザーを検索できます。
特定のIDを持つユーザーを検索する
id が 2 のユーザーを検索する場合は、array_filter() を使って次のように書けます。
$result = array_filter($users, function ($user) {
return $user['id'] === 2;
});
print_r($result);
実行結果は次のとおりです。
Array
(
[1] => Array
(
[id] => 2
[name] => Suzuki
[email] => suzuki@example.com
[role] => editor
)
)
この場合も、array_filter() は元のキーを保持します。
そのため、結果のキーは [0] ではなく [1] になっています。
検索結果から1件だけ取り出す
array_filter() の結果から1件だけ取り出したい場合は、array_values() を使うと扱いやすくなります。
$result = array_filter($users, function ($user) {
return $user['id'] === 2;
});
$user = array_values($result)[0] ?? null;
print_r($user);
実行結果は次のとおりです。
Array
(
[id] => 2
[name] => Suzuki
[email] => suzuki@example.com
[role] => editor
)
?? null を付けておくと、条件に合う要素が見つからなかった場合でもエラーを防ぎやすくなります。
条件に合う最初の1件だけ取得する方法
PHP 8.4以降では array_find() が使える
PHP 8.4以降では、条件に合う最初の要素を取得する array_find() が使えます。
$users = [
['id' => 1, 'name' => 'Tanaka'],
['id' => 2, 'name' => 'Suzuki'],
['id' => 3, 'name' => 'Sato'],
];
$user = array_find($users, function ($user) {
return $user['id'] === 2;
});
print_r($user);
実行結果は次のとおりです。
Array
(
[id] => 2
[name] => Suzuki
)
array_find() は、コールバック関数が true を返した最初の要素を返します。
見つからなかった場合は null を返します。
1件だけ取得したい場合、array_filter() よりも意図がわかりやすい書き方です。
$user = array_find($users, fn($user) => $user['id'] === 2);
PHP 8.3以前では foreach を使う
PHP 8.3以前では array_find() が使えないため、foreach を使う方法が実用的です。
$found = null;
foreach ($users as $user) {
if ($user['id'] === 2) {
$found = $user;
break;
}
}
print_r($found);
実行結果は次のとおりです。
Array
(
[id] => 2
[name] => Suzuki
)
foreach を使う方法は、見つかった時点で break できるため、無駄な処理を減らせます。
大量のデータから1件だけ探す場合は、array_filter() で全件走査して配列を作るよりも、foreach で見つけた時点で処理を止める方が効率的です。
自作関数を作る場合は関数名に注意する
PHP 8.3以前で、array_find() のような処理を使い回したい場合は、自作関数を作ることもできます。
ただし、PHP 8.4以降では array_find() が標準関数として存在します。
そのため、自作関数名を array_find() にすると、関数名が衝突する可能性があります。
自作する場合は、例えば次のように別名にすると安全です。
function find_first(array $array, callable $callback): mixed
{
foreach ($array as $key => $value) {
if ($callback($value, $key)) {
return $value;
}
}
return null;
}
使用例は次のとおりです。
$user = find_first($users, function ($user) {
return $user['id'] === 2;
});
print_r($user);
標準関数と同じ名前を使わないようにすることで、PHPのバージョンアップ時のトラブルを避けやすくなります。
条件に合う最初のキーを取得する方法
PHP 8.4以降では array_find_key() が使える
条件に合う最初の要素のキーを取得したい場合、PHP 8.4以降では array_find_key() が使えます。
$users = [
'user1' => ['id' => 1, 'name' => 'Tanaka'],
'user2' => ['id' => 2, 'name' => 'Suzuki'],
'user3' => ['id' => 3, 'name' => 'Sato'],
];
$key = array_find_key($users, function ($user) {
return $user['id'] === 2;
});
echo $key;
実行結果は次のとおりです。
user2
array_find_key() は、条件に合う最初の要素のキーを返します。
見つからなかった場合は null を返します。
PHP 8.3以前では foreach でキーを取得する
PHP 8.3以前の環境では、foreach を使ってキーを取得します。
$foundKey = null;
foreach ($users as $key => $user) {
if ($user['id'] === 2) {
$foundKey = $key;
break;
}
}
echo $foundKey;
実行結果は次のとおりです。
user2
キーと値の両方を扱いたい場合、foreach ($array as $key => $value) の形が便利です。
条件に合う要素があるか調べる方法
PHP 8.4以降では array_any() が使える
条件に合う要素が1つでも存在するか調べたい場合、PHP 8.4以降では array_any() が使えます。
$users = [
['name' => 'Tanaka', 'role' => 'admin'],
['name' => 'Suzuki', 'role' => 'editor'],
['name' => 'Sato', 'role' => 'editor'],
];
$hasAdmin = array_any($users, function ($user) {
return $user['role'] === 'admin';
});
var_dump($hasAdmin);
実行結果は次のとおりです。
bool(true)
array_any() は、1つでも条件に合う要素があれば true を返します。
「該当データがあるかどうかだけ知りたい」という場合に便利です。
PHP 8.3以前では foreach で判定する
PHP 8.3以前では、foreach で判定できます。
$hasAdmin = false;
foreach ($users as $user) {
if ($user['role'] === 'admin') {
$hasAdmin = true;
break;
}
}
var_dump($hasAdmin);
実行結果は次のとおりです。
bool(true)
見つかった時点で break すれば、それ以上の処理を行わずに済みます。
すべての要素が条件を満たすか調べる方法
PHP 8.4以降では array_all() が使える
すべての要素が条件を満たしているか調べたい場合、PHP 8.4以降では array_all() が使えます。
$users = [
['name' => 'Tanaka', 'age' => 28],
['name' => 'Suzuki', 'age' => 35],
['name' => 'Sato', 'age' => 19],
];
$allAdults = array_all($users, function ($user) {
return $user['age'] >= 20;
});
var_dump($allAdults);
実行結果は次のとおりです。
bool(false)
この例では、Sato の年齢が19歳なので、すべてのユーザーが20歳以上ではありません。
そのため、false が返ります。
PHP 8.3以前では foreach で判定する
PHP 8.3以前では、次のように foreach で判定できます。
$allAdults = true;
foreach ($users as $user) {
if ($user['age'] < 20) {
$allAdults = false;
break;
}
}
var_dump($allAdults);
実行結果は次のとおりです。
bool(false)
条件を満たさない要素が見つかった時点で break できるため、効率的です。
array_column() を使って検索しやすくする方法
特定のカラムだけを取り出す
多次元配列から特定の項目だけを取り出したい場合は、array_column() が便利です。
$users = [
[
'id' => 1,
'name' => 'Tanaka',
'email' => 'tanaka@example.com',
],
[
'id' => 2,
'name' => 'Suzuki',
'email' => 'suzuki@example.com',
],
[
'id' => 3,
'name' => 'Sato',
'email' => 'sato@example.com',
],
];
$names = array_column($users, 'name');
print_r($names);
実行結果は次のとおりです。
Array
(
[0] => Tanaka
[1] => Suzuki
[2] => Sato
)
array_column() を使うと、多次元配列から指定した列だけを取り出せます。
特定カラムの値に含まれるか検索する
名前一覧に Suzuki が含まれているか調べたい場合は、array_column() と in_array() を組み合わせます。
$names = array_column($users, 'name');
if (in_array('Suzuki', $names, true)) {
echo 'Suzukiさんが存在します';
}
実行結果は次のとおりです。
Suzukiさんが存在します
このように、特定の列だけを取り出してから検索すると、コードがわかりやすくなります。
IDをキーにした配列を作る
array_column() の第3引数を使うと、特定の値をキーにした配列を作れます。
$usersById = array_column($users, null, 'id');
print_r($usersById);
実行結果は次のようになります。
Array
(
[1] => Array
(
[id] => 1
[name] => Tanaka
[email] => tanaka@example.com
)
[2] => Array
(
[id] => 2
[name] => Suzuki
[email] => suzuki@example.com
)
[3] => Array
(
[id] => 3
[name] => Sato
[email] => sato@example.com
)
)
こうしておくと、IDから直接データを取り出せます。
$user = $usersById[2] ?? null;
print_r($user);
実行結果は次のとおりです。
Array
(
[id] => 2
[name] => Suzuki
[email] => suzuki@example.com
)
何度もIDで検索する場合は、毎回 array_filter() を使うよりも、あらかじめIDをキーにした配列を作っておくと便利です。
IDが重複する場合は上書きに注意する
array_column($users, null, 'id') は便利ですが、IDが重複している場合は注意が必要です。
$users = [
['id' => 1, 'name' => 'Tanaka'],
['id' => 1, 'name' => 'Suzuki'],
];
$usersById = array_column($users, null, 'id');
print_r($usersById);
実行結果は次のようになります。
Array
(
[1] => Array
(
[id] => 1
[name] => Suzuki
)
)
同じキーがある場合、後の要素で上書きされます。
そのため、array_column($users, null, 'id') は、IDが一意である場合に使うのが基本です。
複数条件で連想配列を検索する方法
array_filter() で複数条件を指定する
複数の条件に合う要素を検索したい場合は、array_filter() のコールバック内で条件を組み合わせます。
例えば、role が editor で、名前が Suzuki のユーザーを探す場合は次のように書きます。
$users = [
[
'id' => 1,
'name' => 'Tanaka',
'role' => 'admin',
],
[
'id' => 2,
'name' => 'Suzuki',
'role' => 'editor',
],
[
'id' => 3,
'name' => 'Sato',
'role' => 'editor',
],
];
$result = array_filter($users, function ($user) {
return $user['role'] === 'editor'
&& $user['name'] === 'Suzuki';
});
print_r($result);
実行結果は次のとおりです。
Array
(
[1] => Array
(
[id] => 2
[name] => Suzuki
[role] => editor
)
)
&& を使うと、複数の条件をすべて満たす要素だけを抽出できます。
外部変数を検索条件に使う
検索条件を変数で指定したい場合は、無名関数で use を使います。
$targetRole = 'editor';
$result = array_filter($users, function ($user) use ($targetRole) {
return $user['role'] === $targetRole;
});
print_r($result);
実行結果は次のようになります。
Array
(
[1] => Array
(
[id] => 2
[name] => Suzuki
[role] => editor
)
[2] => Array
(
[id] => 3
[name] => Sato
[role] => editor
)
)
use ($targetRole) を指定することで、無名関数の外側にある変数を関数内で使えるようになります。
アロー関数で短く書く
PHP 7.4以降では、アロー関数を使って短く書くこともできます。
$targetRole = 'editor';
$result = array_filter($users, fn($user) => $user['role'] === $targetRole);
アロー関数では、外側の変数を自動的に参照できます。
そのため、use ($targetRole) を書く必要がありません。
ただし、処理が複雑になる場合は、通常の無名関数を使った方が読みやすいこともあります。
部分一致で連想配列を検索する方法
str_contains() を使う
文字列の一部が一致するか調べたい場合は、str_contains() を使います。
例えば、名前に Sa を含むユーザーを検索する場合は次のように書きます。
$users = [
['id' => 1, 'name' => 'Tanaka'],
['id' => 2, 'name' => 'Suzuki'],
['id' => 3, 'name' => 'Sato'],
];
$keyword = 'Sa';
$result = array_filter($users, function ($user) use ($keyword) {
return str_contains($user['name'], $keyword);
});
print_r($result);
実行結果は次のとおりです。
Array
(
[2] => Array
(
[id] => 3
[name] => Sato
)
)
str_contains() はPHP 8以降で使える関数です。
PHP 7系では strpos() を使う
PHP 7系など、str_contains() が使えない環境では strpos() を使います。
$keyword = 'Sa';
$result = array_filter($users, function ($user) use ($keyword) {
return strpos($user['name'], $keyword) !== false;
});
strpos() は、文字列が見つかった位置を返します。
見つからなかった場合は false を返します。
そのため、判定には必ず !== false を使います。
strpos($user['name'], $keyword) !== false;
if (strpos(...)) のように書くと、先頭に一致した場合に 0 が返り、誤って false と判定される可能性があります。
前方一致・後方一致で検索する方法
str_starts_with() で前方一致検索をする
キーや値が特定の文字列で始まるか調べたい場合は、str_starts_with() を使います。
$data = [
'user_name' => 'Tanaka',
'user_email' => 'tanaka@example.com',
'admin_name' => 'Suzuki',
];
$result = array_filter(
$data,
function ($key) {
return str_starts_with($key, 'user_');
},
ARRAY_FILTER_USE_KEY
);
print_r($result);
実行結果は次のとおりです。
Array
(
[user_name] => Tanaka
[user_email] => tanaka@example.com
)
str_starts_with() はPHP 8以降で使える関数です。
PHP 7系で同じことをしたい場合は、strpos() を使います。
strpos($key, 'user_') === 0;
str_ends_with() で後方一致検索をする
文字列が特定の文字列で終わるか調べたい場合は、str_ends_with() を使います。
例えば、メールアドレスが @example.com で終わるユーザーを検索する場合は次のように書きます。
$users = [
['name' => 'Tanaka', 'email' => 'tanaka@example.com'],
['name' => 'Suzuki', 'email' => 'suzuki@example.net'],
['name' => 'Sato', 'email' => 'sato@example.com'],
];
$domain = '@example.com';
$result = array_filter($users, function ($user) use ($domain) {
return str_ends_with($user['email'], $domain);
});
print_r($result);
実行結果は次のようになります。
Array
(
[0] => Array
(
[name] => Tanaka
[email] => tanaka@example.com
)
[2] => Array
(
[name] => Sato
[email] => sato@example.com
)
)
str_ends_with() もPHP 8以降で使える関数です。
PHP 7系で書く場合は、次のように substr() を使えます。
substr($email, -strlen($domain)) === $domain;
大文字・小文字を無視して検索する方法
strtolower() を使う
PHPの文字列比較は、基本的に大文字・小文字を区別します。
$user = [
'name' => 'Tanaka',
];
var_dump(in_array('tanaka', $user, true));
実行結果は次のとおりです。
bool(false)
Tanaka と tanaka は別の文字列として扱われます。
大文字・小文字を無視したい場合は、比較前に小文字化します。
$users = [
['name' => 'Tanaka'],
['name' => 'Suzuki'],
];
$keyword = 'tanaka';
$result = array_filter($users, function ($user) use ($keyword) {
return strtolower($user['name']) === strtolower($keyword);
});
print_r($result);
実行結果は次のとおりです。
Array
(
[0] => Array
(
[name] => Tanaka
)
)
日本語やマルチバイト文字を扱う場合は mb_strtolower() を検討する
日本語や全角英字など、マルチバイト文字を含む可能性がある場合は、mb_strtolower() を使うとよいでしょう。
$keyword = 'TANAKA';
$result = array_filter($users, function ($user) use ($keyword) {
return mb_strtolower($user['name']) === mb_strtolower($keyword);
});
日本語そのものには大文字・小文字の概念がない場合も多いですが、全角英字やアルファベットを含むデータでは、表記ゆれ対策として役立ちます。
重複した値を検索する方法
array_search() は最初のキーだけを返す
array_search() は、同じ値が複数ある場合でも、最初に見つかったキーだけを返します。
$data = [
'a' => 'apple',
'b' => 'banana',
'c' => 'apple',
];
$key = array_search('apple', $data, true);
echo $key;
実行結果は次のとおりです。
a
apple は 'a' と 'c' の両方にあります。
しかし、array_search() は最初に見つかった 'a' だけを返します。
同じ値を持つキーをすべて取得する
同じ値を持つキーをすべて取得したい場合は、array_keys() を使います。
$data = [
'a' => 'apple',
'b' => 'banana',
'c' => 'apple',
];
$keys = array_keys($data, 'apple', true);
print_r($keys);
実行結果は次のとおりです。
Array
(
[0] => a
[1] => c
)
array_keys() の第2引数に検索したい値を指定すると、その値を持つキーを取得できます。
第3引数に true を指定すると、型まで含めて厳密に比較できます。
array_flip() を使って検索しやすくする方法
値をキーに変換する
大量のデータに対して、何度も「値が存在するか」を調べたい場合は、array_flip() を使う方法があります。
$allowedRoles = ['admin', 'editor', 'author'];
$allowedRoleMap = array_flip($allowedRoles);
var_dump(isset($allowedRoleMap['editor']));
var_dump(isset($allowedRoleMap['guest']));
実行結果は次のとおりです。
bool(true)
bool(false)
array_flip() を使うと、配列のキーと値が入れ替わります。
[
'admin' => 0,
'editor' => 1,
'author' => 2,
]
こうしておくと、isset() を使ってキーの存在を高速に確認できます。
isset($allowedRoleMap['editor']);
in_array() を何度も実行するより、値をキー化しておいた方が検索しやすい場面があります。
array_flip() の注意点
array_flip() を使う場合は、いくつか注意点があります。
まず、値は文字列または整数である必要があります。
$data = [
['name' => 'Tanaka'],
['name' => 'Suzuki'],
];
$result = array_flip($data);
このように、値が配列やオブジェクトの場合はキーにできません。
また、重複する値がある場合は後の値で上書きされます。
$data = ['admin', 'editor', 'admin'];
$result = array_flip($data);
print_r($result);
実行結果は次のようになります。
Array
(
[admin] => 2
[editor] => 1
)
admin が重複しているため、後のインデックスで上書きされています。
そのため、array_flip() は、値が重複しない前提で使うとよいでしょう。
empty() を使うときの注意点
empty() は存在確認とは意味が違う
PHPでは、値が空かどうかを調べるために empty() を使うことがあります。
$input = [
'name' => 'Tanaka',
'email' => '',
];
if (empty($input['email'])) {
echo 'emailは空です';
}
実行結果は次のとおりです。
emailは空です
ただし、empty() は「キーが存在するか」を調べるものではありません。
あくまで、値が空として扱われるかどうかを判定するものです。
empty() で空扱いされる値
empty() は、次のような値を空として扱います。
''
0
'0'
null
false
[]
例えば、次のコードを見てください。
$data = [
'count' => 0,
];
if (empty($data['count'])) {
echo 'countは空です';
}
実行結果は次のとおりです。
countは空です
count というキーは存在しています。
値も 0 として意味があるかもしれません。
しかし、empty() では 0 が空として扱われるため、true になります。
存在確認と空判定は分けて考える
連想配列を扱うときは、存在確認と空判定を分けて考えることが大切です。
$data = [
'count' => 0,
];
// キーが存在するか
array_key_exists('count', $data);
// 値がnullではないか
isset($data['count']);
// 空文字ではないか
$data['count'] !== '';
フォーム入力やAPIレスポンスでは、0、false、空文字、null の意味がそれぞれ異なることがあります。
そのため、単純に empty() だけで判定すると、意図しない結果になる場合があります。
実務でよく使う連想配列検索の例
設定配列にキーがあるか調べる
設定配列では、値が false でも意味を持つ場合があります。
$config = [
'debug' => true,
'timezone' => 'Asia/Tokyo',
'cache' => false,
];
if (array_key_exists('cache', $config)) {
echo 'cache設定があります';
}
実行結果は次のとおりです。
cache設定があります
この場合、cache の値は false ですが、キー自体は存在します。
そのため、設定項目の存在確認には array_key_exists() が向いています。
フォーム入力に項目があるか調べる
フォーム入力では、項目が送信されたかどうかを確認したいことがあります。
$input = [
'name' => 'Tanaka',
'email' => '',
];
if (array_key_exists('email', $input)) {
echo 'email項目は送信されています';
}
実行結果は次のとおりです。
email項目は送信されています
この例では、email の値は空文字です。
しかし、email という項目は送信されています。
「項目があるか」と「値が空でないか」は別の判定です。
// 項目が送信されたか
array_key_exists('email', $input);
// 値が空でないか
$input['email'] !== '';
このように、目的に応じて判定方法を分けましょう。
APIレスポンスから特定データを探す
APIレスポンスの中から、特定のIDを持つデータを探すケースもよくあります。
$response = [
'status' => 'success',
'data' => [
['id' => 1, 'title' => 'Article A'],
['id' => 2, 'title' => 'Article B'],
['id' => 3, 'title' => 'Article C'],
],
];
$article = null;
foreach ($response['data'] as $item) {
if ($item['id'] === 2) {
$article = $item;
break;
}
}
print_r($article);
実行結果は次のとおりです。
Array
(
[id] => 2
[title] => Article B
)
1件だけ取得したい場合は、foreach + break がシンプルでわかりやすいです。
PHP 8.4以降であれば、次のように array_find() を使うこともできます。
$article = array_find($response['data'], fn($item) => $item['id'] === 2);
WordPressの配列から設定値を探す
WordPressでは、投稿データ、メタ情報、オプション値などで連想配列を扱うことがあります。
$meta = [
'description' => '記事の説明文',
'keywords' => 'PHP,WordPress,SEO',
'noindex' => false,
];
if (array_key_exists('noindex', $meta)) {
echo 'noindex設定があります';
}
実行結果は次のとおりです。
noindex設定があります
SEO設定などでは、false という値にも意味があります。
そのため、存在確認に empty() を使うと誤判定になる場合があります。
if (empty($meta['noindex'])) {
echo 'noindexは空です';
}
この場合、false は空として扱われます。
設定項目が存在するか確認したい場合は、次のように書く方が安全です。
array_key_exists('noindex', $meta);
値が true かどうかを確認したい場合は、次のように厳密に比較します。
$meta['noindex'] === true;
PHPの連想配列検索でよくあるミス
array_search() の結果を if ($key) で判定してしまう
array_search() の結果を次のように判定するのは避けましょう。
$key = array_search('apple', $data, true);
if ($key) {
echo '見つかりました';
}
キーが 0 の場合、見つかっていても false と判定される可能性があります。
正しくは、次のように書きます。
if ($key !== false) {
echo '見つかりました';
}
in_array() の第3引数を省略してしまう
in_array() の第3引数を省略すると、型変換によって意図しない一致が起きる場合があります。
in_array(1, ['1']);
この場合、true になる可能性があります。
厳密に比較したい場合は、次のように書きます。
in_array(1, ['1'], true);
実務では、基本的に第3引数に true を指定するのがおすすめです。
isset() と array_key_exists() を混同してしまう
isset() と array_key_exists() は似ていますが、null の扱いが異なります。
$data = [
'name' => null,
];
var_dump(isset($data['name']));
var_dump(array_key_exists('name', $data));
実行結果は次のとおりです。
bool(false)
bool(true)
値が null の可能性がある場合は、isset() だけでキーの存在を判断しないようにしましょう。
array_filter() 後のキーを意識していない
array_filter() は、元のキーを保持します。
$numbers = [10, 20, 30, 40];
$result = array_filter($numbers, fn($number) => $number >= 30);
print_r($result);
実行結果は次のとおりです。
Array
(
[2] => 30
[3] => 40
)
連番の配列として扱いたい場合は、array_values() を使います。
$result = array_values($result);
特に、JSONとして返す場合は注意しましょう。
array_column() のキー重複を見落としてしまう
array_column($users, null, 'id') は便利ですが、キーに指定した値が重複していると上書きされます。
$users = [
['id' => 1, 'name' => 'Tanaka'],
['id' => 1, 'name' => 'Suzuki'],
];
$usersById = array_column($users, null, 'id');
この場合、id が同じなので、後の Suzuki のデータで上書きされます。
IDが一意でない場合は、array_filter() やグルーピング処理を使う方が安全です。
PHPバージョン別の検索方法
PHP 8.4以降で使いやすい関数
PHP 8.4以降では、配列検索に便利な関数が追加されています。
| 関数 | 役割 |
|---|---|
array_find() | 条件に合う最初の値を返す |
array_find_key() | 条件に合う最初のキーを返す |
array_any() | 条件に合う要素が1つでもあれば true |
array_all() | すべての要素が条件を満たせば true |
例えば、条件に合う最初のユーザーを取得する場合は次のように書けます。
$user = array_find($users, fn($user) => $user['id'] === 2);
条件に合う要素があるかだけを調べる場合は、次のように書けます。
$hasAdmin = array_any($users, fn($user) => $user['role'] === 'admin');
PHP 8.4以降を前提にできる環境では、これらの関数を使うとコードが読みやすくなります。
PHP 8.3以前でも使える方法
PHP 8.3以前では、array_find() や array_any() は使えません。
そのため、次のような方法を使います。
// 条件に合う最初の1件を取得
$found = null;
foreach ($users as $user) {
if ($user['id'] === 2) {
$found = $user;
break;
}
}
// 条件に合う要素をすべて取得
$result = array_filter($users, fn($user) => $user['role'] === 'editor');
// 値が存在するか確認
in_array($value, $array, true);
// キーが存在するか確認
array_key_exists($key, $array);
古いPHP環境も考慮する必要がある場合は、foreach、array_filter()、array_search()、in_array() を中心に使うとよいでしょう。
目的別の使い分けまとめ
キーが存在するか調べたい場合
キーが存在するか調べたい場合は、array_key_exists() を使います。
array_key_exists('name', $array);
値が null でもキーの存在を確認できます。
キーがあり、値が null でないか調べたい場合
値が null ではないことも確認したい場合は、isset() を使います。
isset($array['name']);
ただし、値が null の場合は false になる点に注意しましょう。
値が存在するか調べたい場合
値が配列内に存在するか調べたい場合は、in_array() を使います。
in_array('Tanaka', $array, true);
第3引数には true を指定し、厳密比較にするのがおすすめです。
値からキーを取得したい場合
値からキーを取得したい場合は、array_search() を使います。
$key = array_search('Tanaka', $array, true);
判定するときは、必ず !== false を使います。
if ($key !== false) {
// 見つかった場合の処理
}
条件に合う要素をすべて取得したい場合
条件に合う要素をすべて取得したい場合は、array_filter() を使います。
$result = array_filter($array, function ($item) {
return 条件;
});
array_filter() はキーを保持するため、必要に応じて array_values() を使いましょう。
$result = array_values($result);
条件に合う最初の1件を取得したい場合
PHP 8.4以降では、array_find() が使えます。
$found = array_find($array, function ($item) {
return 条件;
});
PHP 8.3以前では、foreach を使います。
$found = null;
foreach ($array as $item) {
if (条件) {
$found = $item;
break;
}
}
条件に合う最初のキーを取得したい場合
PHP 8.4以降では、array_find_key() が使えます。
$key = array_find_key($array, function ($item) {
return 条件;
});
PHP 8.3以前では、foreach でキーを取得します。
$foundKey = null;
foreach ($array as $key => $item) {
if (条件) {
$foundKey = $key;
break;
}
}
多次元配列の特定カラムを検索したい場合
特定の列だけを取り出したい場合は、array_column() を使います。
$names = array_column($users, 'name');
取り出した値に対して検索したい場合は、in_array() と組み合わせます。
in_array('Suzuki', $names, true);
IDをキーにした配列を作りたい場合は、次のように書きます。
$usersById = array_column($users, null, 'id');
ただし、IDが重複する場合は上書きされるため注意が必要です。
まとめ
PHPの連想配列検索は目的に応じて関数を使い分ける
PHPの連想配列検索では、何を探したいかによって使う関数が変わります。
キーを探したい場合は array_key_exists() や isset()、値を探したい場合は in_array()、値からキーを取得したい場合は array_search() を使います。
条件に合う要素を取り出したい場合は array_filter() が便利です。
また、PHP 8.4以降では、条件に合う最初の要素を取得する array_find() や、条件に合う最初のキーを取得する array_find_key() も使えます。
基本の使い分け
PHPの連想配列検索では、次の使い分けを覚えておくと便利です。
// キーが存在するか
array_key_exists('key', $array);
// キーがあり、値がnullではないか
isset($array['key']);
// 値が存在するか
in_array($value, $array, true);
// 値に対応するキーを取得
array_search($value, $array, true);
// 条件に合う要素をすべて取得
array_filter($array, fn($item) => 条件);
// PHP 8.4以降で、条件に合う最初の値を取得
array_find($array, fn($item) => 条件);
// PHP 8.4以降で、条件に合う最初のキーを取得
array_find_key($array, fn($item) => 条件);
実務では厳密比較と戻り値の判定に注意する
実務で特に注意したいのは、次の3点です。
// in_array() は第3引数 true を付ける
in_array($value, $array, true);
// array_search() は !== false で判定する
$key = array_search($value, $array, true);
if ($key !== false) {
// 見つかった
}
// array_filter() 後に必要なら array_values() でキーを振り直す
$result = array_values($result);
PHPの配列検索では、0、false、null、空文字などの扱いで誤判定が起きやすいです。
そのため、型まで含めて比較すること、戻り値を正しく判定すること、キーが保持される仕様を理解することが重要です。
連想配列の検索を正しく使い分けられるようになると、フォーム処理、APIレスポンス処理、設定配列の管理、WordPressのカスタマイズなど、さまざまな場面で安全で読みやすいコードを書けるようになります。
以上、PHPの連想配列の検索についてでした。
最後までお読みいただき、ありがとうございました。










