array_intersect() / array_diff()
| 対応: | PHP 4(2000) |
|---|
複数の配列の共通要素や差分を取得する関数です。値による比較とキーによる比較の両方に対応しています。
構文
// 値を比較して共通する要素を取得 array_intersect(配列1, 配列2, ...); // 値を比較して差分の要素を取得 array_diff(配列1, 配列2, ...); // キーを比較して共通する要素を取得 array_intersect_key(配列1, 配列2, ...); // キーを比較して差分の要素を取得 array_diff_key(配列1, 配列2, ...);
関数一覧
| 関数 | 概要 |
|---|---|
| array_intersect($array1, $array2, ...) | 配列の値を比較し、すべての配列に共通する値を持つ要素を返します。キーは最初の配列のものが保持されます。 |
| array_diff($array1, $array2, ...) | 配列の値を比較し、最初の配列にあって他の配列にない要素を返します。 |
| array_intersect_key($array1, $array2, ...) | 配列のキーを比較し、共通するキーを持つ要素を最初の配列から返します。 |
| array_diff_key($array1, $array2, ...) | 配列のキーを比較し、最初の配列にあって他の配列にないキーの要素を返します。 |
サンプルコード
値の比較(array_intersect / array_diff)
夜神月と弥海砂の好きなキャラ名リストを比較して、共通するものと差分を取得します。
sample_array_intersect.php
<?php $light_favorites = ['夜神月', 'L', '弥海砂', '弥彦']; $misa_favorites = ['弥海砂', '弥彦', '松田桃李', 'L']; // 両方に共通するキャラを取得 $common = array_intersect($light_favorites, $misa_favorites); print_r($common); // 月リストにあってミサリストにないものを取得 $only_light = array_diff($light_favorites, $misa_favorites); print_r($only_light);
実行すると次のように出力されます。
php sample_array_intersect.php
Array
(
[1] => L
[2] => 弥海砂
[3] => 弥彦
)
Array
(
[0] => 夜神月
)
キーの比較(array_intersect_key / array_diff_key)
設定配列のキーを比較して、共通するキー・差分のキーを持つ要素を取り出します。
sample_array_intersect_key.php
<?php $old_settings = ['theme' => 'dark', 'lang' => 'ja', 'font_size' => 14]; $new_settings = ['theme' => 'light', 'lang' => 'en', 'sidebar' => true]; // 共通するキーの要素を取得(値は最初の配列から) $common_keys = array_intersect_key($old_settings, $new_settings); print_r($common_keys); // 古い設定にあって新しい設定にないキーを取得 $removed = array_diff_key($old_settings, $new_settings); print_r($removed); // 新しい設定にあって古い設定にないキーを取得 $added = array_diff_key($new_settings, $old_settings); print_r($added);
実行すると次のように出力されます。
php sample_array_intersect_key.php
Array
(
[theme] => dark
[lang] => ja
)
Array
(
[font_size] => 14
)
Array
(
[sidebar] => 1
)
実践的な使い方(権限チェック)
ユーザーが持つ権限リストと操作に必要な権限リストを照合して、すべての権限を持つか確認します。
sample_permission_check.php
<?php
$user_roles = ['read', 'write', 'delete'];
$required_roles = ['write', 'delete'];
$matched = array_intersect($required_roles, $user_roles);
if (count($matched) === count($required_roles)) {
echo 'アクセス許可';
} else {
echo 'アクセス拒否';
}
実行すると次のように出力されます。
php sample_permission_check.php アクセス許可
概要
『array_intersect()』と『array_diff()』は配列の値を比較する関数で、返される配列のキーは最初の配列のものが保持されます。キーが飛び飛びになるため、必要に応じて『array_values()』で振り直すことができます。
『array_intersect_key()』と『array_diff_key()』はキーを基準に比較を行います。返される値は最初の配列のものであり、2番目以降の配列の値は使用されません。設定の差分検出やデータのマージ処理で活用できます。
値とキーの両方を同時に比較したい場合は『array_intersect_assoc()』や『array_diff_assoc()』を使うことができます。配列内の特定の値を検索する場合は『in_array() / array_search()』が適しています。
キーが飛び飛びになる
『array_intersect()』と『array_diff()』の結果は、元の配列のキーが保持されます。そのため、返される配列のキーが0から始まらず飛び飛びになることがあります。連番のキーが必要な場合は『array_values()』で振り直すことができます。
sample.php
<?php $suspects = ['夜神月', 'L', '弥海砂', '弥彦', '松田桃李']; $kira = ['夜神月', '弥海砂']; // array_diffの結果はキーが保持される $non_kira = array_diff($suspects, $kira); print_r($non_kira);
実行すると次のように出力されます。
php sample.php
Array
(
[1] => L
[3] => 弥彦
[4] => 松田桃李
)
キーを0から振り直したい場合は『array_values()』を使います。
sample_02.php
<?php $suspects = ['夜神月', 'L', '弥海砂', '弥彦', '松田桃李']; $kira = ['夜神月', '弥海砂']; $non_kira = array_values(array_diff($suspects, $kira)); print_r($non_kira);
実行すると次のように出力されます。
php sample_02.php
Array
(
[0] => L
[1] => 弥彦
[2] => 松田桃李
)
空配列との比較でも正常動作する
空配列を引数として渡した場合、エラーにはならず空の配列が返されます。
sample_03.php
<?php $suspects = ['夜神月', 'L', '弥海砂']; $empty = []; // 空配列との共通部分は空 $result = array_intersect($suspects, $empty); print_r($result); // 空配列との差分は元の配列がそのまま返る $result2 = array_diff($suspects, $empty); print_r($result2);
実行すると次のように出力されます。
php sample_03.php
Array
(
)
Array
(
[0] => 夜神月
[1] => L
[2] => 弥海砂
)
厳密な型比較が行われない
『array_intersect()』はデフォルトで文字列比較を行うため、整数の『1』と文字列の『"1"』が同じとみなされます。型も含めて比較したい場合、『array_intersect_strict()』は存在しないため、『array_filter()』と『in_array()』を組み合わせて自前実装することになります。
sample_04.php
<?php $a = [1, 2, 3]; $b = ['1', '2', '4']; // デフォルトは文字列比較なので 1 と "1" が一致する $common = array_intersect($a, $b); print_r($common);
実行すると次のように出力されます。
php sample_04.php
Array
(
[0] => 1
[1] => 2
)
型も含めて厳密に比較したい場合は、コールバックで自前実装します。
sample_05.php
<?php
$a = [1, 2, 3];
$b = ['1', '2', '4'];
// 型も含めた厳密比較(array_intersect_strictは存在しないため自前実装)
$strict_common = array_filter($a, function($val) use ($b) {
return in_array($val, $b, true);
});
print_r($strict_common);
実行すると次のように出力されます。
php sample_05.php Array ( )
実践パターン
権限システム:ユーザー権限と必要権限の照合
ユーザーが持つ権限リストと、特定の操作に必要な権限リストを照合して、アクセス可否を判定します。
sample_06.php
<?php
function has_required_roles($user_roles, $required_roles) {
$matched = array_intersect($required_roles, $user_roles);
return count($matched) === count($required_roles);
}
$light_roles = ['read', 'write', 'admin'];
$l_roles = ['read'];
// 管理操作(write + admin が必要)
$required = ['write', 'admin'];
echo has_required_roles($light_roles, $required) ? '月: アクセス許可' : '月: アクセス拒否';
echo "\n";
echo has_required_roles($l_roles, $required) ? 'L: アクセス許可' : 'L: アクセス拒否';
実行すると次のように出力されます。
php sample_06.php 月: アクセス許可 L: アクセス拒否
タグフィルタリング:記事タグと選択済みタグの共通部分
ユーザーが選択したタグと記事のタグを照合して、条件に合う記事を抽出します。
sample_07.php
<?php
$articles = [
['title' => '死神の目について', 'tags' => ['キラ', '死神', '取引']],
['title' => 'Lの推理', 'tags' => ['捜査', 'L', '推理']],
['title' => 'キラ捜査の真実', 'tags' => ['キラ', '捜査', '真実']],
];
$selected_tags = ['キラ', '捜査'];
$matched_articles = array_filter($articles, function($article) use ($selected_tags) {
return count(array_intersect($article['tags'], $selected_tags)) > 0;
});
foreach ($matched_articles as $article) {
echo $article['title'] . "\n";
}
実行すると次のように出力されます。
php sample_07.php 死神の目について Lの推理 キラ捜査の真実
記事の間違いや著作権の侵害等ございましたらお手数ですがこちらまでご連絡頂ければ幸いです。