はじめに
PHPの配列マージで新しい発見があったのでのまとめ
やりたかったこと
設定ファイルの上書きで、envファイルのような仕組みがなかったので自作する。
配列で管理している設定ファイルに対して、別ファイルを用意して設定内容を上書きする。
設定内容は階層がまばらなため、多次元配列で管理。
欲しい結果例
# ベースの設定
$base = [
"db" => [
"adapter" => "pdo_mysql",
"params" => [
"host" => "production.db.xxxxxx",
"user" => "db_user",
"dbname" => "prod_db",
"password" => "xyz12345"
]
]
];
# 上書き内容 (hostとdbnameのみ上書き)
$env = [
"db" => [
"params" => [
"host" => "localhost",
"dbname" => "local_db"
]
]
];
# 欲しい結果
$result = [
"db" => [
"adapter" => "pdo_mysql",
"params" => [
"host" => "localhost",
"user" => "db_user",
"dbname" => "local_db",
"password" => "xyz12345"
]
]
];
array_merge()
再帰処理は行わず、第1階層の同一キーの要素を上書き。
※ キーが数値の場合は、キーがゼロから始まる連続した数値に置き換えられ、後の配列が前の配列の後ろに追加される。
$result = array_merge($base, $env);
echo print_r($result, 1);
# 出力結果
Array
(
[db] => Array
(
[params] => Array
(
[host] => localhost
[dbname] => local_db
)
)
)
array_merge_recursive()
再帰処理でマージを行ない、同一キーの要素は上書きではなく、前の配列の値を残した形で追加される。
$result = array_merge_recursive($base, $env);
echo print_r($result, 1);
# 出力結果
Array
(
[db] => Array
(
[adapter] => pdo_mysql
[params] => Array
(
[host] => Array
(
[0] => production.db.xxxxxx
[1] => localhost
)
[user] => db_user
[dbname] => Array
(
[0] => prod_db
[1] => local_db
)
[password] => xyz12345
)
)
)
array_replace()
再帰処理は行わず、第1階層の同一キーの要素を上書き。(キーが文字列の場合、array_mergeと同じ挙動)
※ キーが数字の場合でも、同一キーであれば上書きを実施。
$result = array_merge_recursive($base, $env);
echo print_r($result, 1);
# 出力結果
Array
(
[db] => Array
(
[params] => Array
(
[host] => localhost
[dbname] => local_db
)
)
)
array_replace_recursive()
再帰処理で同一キーの要素を上書き。
$result = array_replace_recursive($base, $env);
echo print_r($result, 1);
# 出力結果
Array
(
[db] => Array
(
[adapter] => pdo_mysql
[params] => Array
(
[host] => localhost
[user] => db_user
[dbname] => local_db
[password] => xyz12345
)
)
)
結論
今回やりたかったことは、array_replace_recursive()で実現できる。
array_mergeはキーが数字の場合の挙動に要注意。