所以,我有三个数组:
$ foo的
Array
(
[0] => Array
(
[sum] => 281
[status] => 0
)
[1] => Array
(
[sum] => 1534
[status] => 1
)
[2] => Array
(
[sum] => 1434
[status] => 2
)
[3] => Array
(
[sum] => 2468
[status] => 3
)
)
$岩石
Array
(
[0] => Array
(
[sum] => 514
[status] => 0
)
[1] => Array
(
[sum] => 500
[status] => 1
)
)
$杆
Array
(
[0] => Array
(
[sum] => 458
[status] => 0
)
[1] => Array
(
[sum] => 500
[status] => 1
)
)
我需要将$bar
和$rock
与$foo
合并,以便添加密钥总和。
例如:
合并$bar
和$rock
与$foo
时,status
为0的第一个索引看起来像这样:
[0] => Array
(
[sum] => 1253 (281 + 514 + 458)
[status] => 0
)
合并应该基于status
。来自status
的{{1}} 0将合并到$rock
的{{1}} 0
我在想是否这是一个递归应用程序并使事情变得更复杂。
我应该如何以简单优化的方式解决它?
答案 0 :(得分:1)
我一直都是可以在将来使用的一般用途功能的粉丝。该解决方案有三个参数:
1)需要组合的所有数组的数组
2)将用作比较基础的密钥(具有密钥的两个节点将被组合)
3)数据键,如果节点“相等”,将是组合的字段
最后,php非常擅长制作字典/散列图。当我们组合数组时,这将有所帮助,因为我们不需要做太多的搜索。
/**
* $arrays - an array of arrays to be combined
* $key - a key in the array that represents the key that holds the values that need to be compared
* $data - a key in the array that represens the key that holds the data
*/
function combine($arrays, $key, $data) {
$ans = array();
//Go through each array that needs to be combined
foreach($arrays as $nodes) {
//go through each node of the array
foreach($nodes as $node) {
//make sure the node actually has the key we need
if (isset($node[$key])) {
//initialize the answer to a new node(array with key, data)
$ansKey = $node[$key];
if (!isset($ans[$node[$key]])) {
$ans[$ansKey] = array();
$ans[$ansKey][$key] = $node[$key];
$ans[$ansKey][$data] = 0;
}
//make sure the node actually has the data we need
if (isset($node[$data])) {
//combined the data
$ans[$ansKey][$data] += $node[$data];
}
}
}
}
//we only care about the nodes, not the ansKeys we used to get there
return array_values($ans);
}
在您的示例中,您可以拨打combine(array($rock, $foo, $bar), "status", "sum")
此函数应为O(n)
,其中n
是节点数。每个节点只处理一次,因为php数组有一个O(1)的查找,我们不会浪费时间搜索以前的值,因为所有的查找都是在数组索引而不是数组值上完成的。
当我使用您的数据运行该函数时,它返回 -
Array
(
[0] => Array
(
[status] => 0
[sum] => 1253
)
[1] => Array
(
[status] => 1
[sum] => 2534
)
[2] => Array
(
[status] => 2
[sum] => 1434
)
[3] => Array
(
[status] => 3
[sum] => 2468
)
)