[英]How to merge two multidimensional arrays without overwriting existing keys in PHP?
我正在嘗試添加兩個多維數組。 該函數應該與將數組加在一起完全相同,如下所示:$new_array = $array1 + $array2,除了它應該與多維數組一起使用。 這意味着 $array2 不應覆蓋現有的鍵值。
示例:假設我有以下 $default_array:
array
'something' => int 0
'nested' =>
array (size=3)
'a' => null
'b' => null
'c' => null
以及以下 $user_array:
array
'something' => int 1000
'nested' =>
array (size=3)
'a' => 1
'new' => int 4
將兩者加在一起(如 $user_array + $default_array)應該給我:
array (size=4)
'something' => int 1000
'nested' =>
array (size=3)
'a' => 1
'b' => null
'c' => null
'new' => int 4
目前,似乎如果我添加兩個多維數組,覆蓋功能似乎只適用於第一個數組維度。 這意味着在這種情況下,'nested' 已經存在於 $user_array 中,因此它不會附加其他值。
編輯:我還應該提到這需要使用無限數量的維度。
編輯 2:我只是嘗試應用 Rain 的答案,但它沒有按預期工作。 首先,我收到“未定義索引”通知。 其次,輸出不是我想要的。 考慮以下數組:
$default = array(
'a' => array(
'a' => 'a',
'b' => 'b',
'c' => 'c',
),
);
$user = array(
'b' => 1,
'a' => array(
'b' => 'something',
'c' => 'something else',
'd' => 'd',
),
'c' => 2);
我用 Rain 的函數得到的輸出是這樣的:
array (size=3)
'a' =>
array (size=3)
'a' => string 'a' (length=1)
'b' => string 'b' (length=1)
'c' => string 'c' (length=1)
'b' => int 1
'c' => int 2
在這個例子中,子數組中的 'b' 和 'c' 鍵應該分別是 'something' 和 'something else'。 我不太確定如何解決這個問題。
您可以嘗試使用array_merge_recursive()
(不僅僅是 array_merge())http://www.php.net/manual/en/function.array-merge-recursive.php
<?php
$defaultarray = array(
'something' => 0,
'nested' =>
array (
'a' => null,
'b' => null,
'c' => null));
$newArray = array(
'something' => 1000,
'nested' =>
array ('a' => 1,
'new' => 4));
$mergedArray = array_merge_recursive($defaultarray, $newArray);
echo print_r($mergedArray,true);
?>
輸出:數組 ( [something] => Array ( [0] => 0 [1] => 1000 ) [嵌套] => Array ( [a] => Array ( [0] => [1] => 1 ) [b] => [c] => [新] => 4 ) )
遞歸函數絕對是這里的方法。 我只是提出了以下內容。 注意fill_in_aux
的函數聲明中&
的使用。 這會導致第二個參數(稱為$default
)通過引用傳遞,而不是通過值傳遞。 它包含在fill_in
因此不會修改真正的“默認”數組。
function fill_in($user, $default) {
fill_in_aux($user, $default);
return $default;
}
function fill_in_aux($user, &$default) {
foreach ($user as $key => $value) {
if (is_array($value)) {
fill_in_aux($user[$key], $default[$key]);
} else {
$default[$key] = $value;
}
}
}
這個假設是在設置任何$default
數組應該被任何存在於被覆蓋$user
數組,即使在一個關鍵$user
數組被設置為null
。 要更改此行為,請在fill_in_aux
的else
子句中添加另一個if
語句。
使用您的示例數組,輸出
print_r(fill_in($user_array, $default_array));
是
Array
(
[something] => 1000
[nested] => Array
(
[a] => 1
[b] =>
[c] =>
)
[new] => 4
)
通常,在 PHP 中調用函數時,參數是按值傳遞的:函數獲取傳入變量的副本。 這意味着函數可以對參數做任何它想做的事情,但是當函數返回時,傳遞的原始變量不受影響。
當參數以&
符號開頭時,參數通過引用傳遞,而不是被復制。 當函數對參數進行修改時,它實際上是直接對傳入的變量進行更改。
有關更多信息,請查看: http : //php.net/manual/en/language.references.pass.php
我很驚訝七年前沒有人向您提供原生函數array_replace_recursive()
。 @bestprogrammerintheworld 在正確的軌道上,但選擇了錯誤的遞歸調用。
使用除此函數之外的任何內容都將導致不必要的代碼膨脹,並且很可能會導致性能下降。
代碼:(演示)
var_export(
array_replace_recursive($default, $user)
);
輸出:
array (
'a' =>
array (
'a' => 'a',
'b' => 'something',
'c' => 'something else',
'd' => 'd',
),
'b' => 1,
'c' => 2,
)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.