array_merge()は文字列キーが同じだと上書きし、数値キーは振り直す
array_merge()は文字列キーが重複していると後の配列の値で上書きし、数値キーは重複を無視して0から振り直します。片方の配列のデータが消えたように見えるのは、この仕様が原因です。
なぜエラーが出ないのか
出力: ,
(エラーなし)- PHPは何も報告しません。文法として正しいためです
出力: ,- 実際の挙動 — 期待した結果と食い違っている箇所
見つけ方- エラーが出ないので、出力を目で確かめるか、コードを目で追うしかありません。この種の誤りが最も発見が遅れます
このエラーが出る典型パターン
パターン1
1 <?php 2 $defaults = ["theme" => "light", "size" => "M"]; 3 $custom = ["theme" => "dark"]; 4 $merged = array_diff ($defaults, $custom); ^ 5 echo $merged["theme"] . "," . $merged["size"];
出力: ,期待: dark,M (エラーにはなりません)
array_diffは差分を取る関数で、意図したマージにはなりません。同じ文字列キーを持つ配列を後勝ちで統合したい場合はarray_mergeを使います。
直し方: array_diff を array_merge にします。
広告
広告スロット(未設定)
パターン2
1 <?php 2 $a = ["x" => 1, "y" => 2]; 3 $b = ["y" => 99, "z" => 4]; ^ 4 $merged = array_merge($a, $b); 5 echo $merged["x"] . "," . $merged["y"] . "," . $merged["z"];
出力: 1,99,4期待: 1,3,4 (エラーにはなりません)
array_mergeは文字列キー"y"が両方の配列にある場合、後の配列($b)の値で上書きします。意図した値を後の配列に渡す必要があります。
直し方: 99 を 3 にします。
パターン3
1 <?php 2 $base = [10, 20]; 3 $extra = [30, 40]; 4 $merged = array_merge($base, $extra); 5 echo count($merged) . ":" . $merged[0] ; ^
出力: 4:10期待: 4:10,20,30,40 (エラーにはなりません)
数値キーの配列同士をarray_mergeすると、キーは0から振り直されて連結されます(この点は文字列キーと違い上書きされません)。全要素を確認するにはimplodeで並べて出力する必要があります。
直し方: $merged[0] を implode(",", $merged) にします。
よくある誤解
「array_mergeは両方の配列のすべての要素を残してくれるはず」という思い込みは誤りです。文字列キーが衝突すれば後勝ちで上書きされ、データが失われます。キーを保持したい場合は+演算子を使う必要があります。
まとめ
array_merge()は文字列キーが同じだと上書きし、数値キーは振り直すは中級でつまずきやすい項目です。上の3パターンを実際に手で直すと、エラーメッセージのどこを読めばよいかが掴めます。