PHP减去数组值

2022-01-17 00:00:00 arrays numbers integer subtraction php

我有一个包含键和值的数组.每个值都是一个整数.我有另一个具有相同键的数组.如何减去匹配键的所有值?也可能有第二个数组中没有出现的键,但两个数组的长度相同.如果数组 2 中有一个键在数组 1 中不存在,则其值应保持不变.如果第一个数组中有一个键不在第二个数组中,则应将其丢弃.我该怎么做?是否有任何内置功能?

I have an array with keys and values. Each value is an integer. I have an other array with the same keys. How can I subtract all of the values for the matching keys? Also there might be keys that do not occur in the second array but both arrays have the same length. If there is a key in array 2 that is not present in array 1 its value should be unchanged. If there is a key in the first array that is not in the second it should be thrown away. How do I do it? Is there any built-in function for this?

如果我要编写一个脚本,它会是这样的某种 for 循环:

If I would write a script it would be some kind of for loop like this:

$arr1 = array('a' => 1, 'b' => 3, 'c' => 10);
$arr2 = array('a' => 2, 'b' => 1, 'c' => 5);
$ret = array();
foreach ($arr1 as $key => $value) {
    $ret[$key] = $arr2[$key] - $arr1[$key];
}
print_r($ret);
/*
should be: array('a' => 1, 'b' => -2, 'c' => -5)
*/

我没有在这里添加一个键在一个数组中而不在另一个数组中.

I did not add the occasion here a key is in one array and not in the other.

推荐答案

如果你愿意的话,你可以避免使用数组函数的 foreach.

You could avoid the foreach using array functions if you were so inclined.

提供给 array_mapdocs 下面将从每个对应的 $arr2 中减去每个 $arr1 值.不幸的是,当使用多个输入数组时,array_map 不会保留您的密钥,因此我们使用 array_combinedocs 将减去的结果合并回带有原始键的数组:

The closure provided to array_mapdocs below will subtract each $arr1 value from each corresponding $arr2. Unfortunately array_map won't preserve your keys when using more than one input array, so we use array_combinedocs to merge the subtracted results back into an array with the original keys:

$arr1 = array('a' => 1, 'b' => 3, 'c' => 10);
$arr2 = array('a' => 2, 'b' => 1, 'c' => 5);

$subtracted = array_map(function ($x, $y) { return $y-$x; } , $arr1, $arr2);
$result     = array_combine(array_keys($arr1), $subtracted);

var_dump($result);

更新

我对数组函数方法与简单的 foreach 相比如何比较感兴趣,因此我使用 Xdebug 对两者进行了基准测试.这是测试代码:

I was interested in how the array functions approach compared to a simple foreach, so I benchmarked both using Xdebug. Here's the test code:

$arr1 = array('a' => 1, 'b' => 3, 'c' => 10);
$arr2 = array('a' => 2, 'b' => 1, 'c' => 5);

function arrayFunc($arr1, $arr2) {
  $subtracted = array_map(function ($x, $y) { return $y-$x; } , $arr1, $arr2);
  $result     = array_combine(array_keys($arr1), $subtracted);
}

function foreachFunc($arr1, $arr2) {
  $ret = array();
  foreach ($arr1 as $key => $value) {
    $ret[$key] = $arr2[$key] - $arr1[$key];
  }
}

for ($i=0;$i<10000;$i++) { arrayFunc($arr1, $arr2); }
for ($i=0;$i<10000;$i++) { foreachFunc($arr1, $arr2); }

事实证明,使用 foreach 循环比使用数组函数完成相同任务快一个数量级.从下面的KCachegrind被调用图可以看出,上面代码中,数组函数方法需要将近80%的处理时间,而foreach函数只需要不到5%.

As it turns out, using the foreach loop is an order of magnitude faster than accomplishing the same task using array functions. As you can see from the below KCachegrind callee image, the array function method required nearly 80% of the processing time in the above code, while the foreach function required less than 5%.

这里的教训:有时语义数组函数(令人惊讶?)在性能方面可能不如 PHP 中良好的老式循环.当然,您应该始终选择更具可读性/语义的选项;如果像这样的微优化会使代码在六个月后更难理解,那么它们是不合理的.

The lesson here: sometimes the more semantic array functions (surprisingly?) can be inferior performance-wise to a good old fashioned loop in PHP. Of course, you should always choose the option that is more readable/semantic; micro-optimizations like this aren't justified if they make the code more difficult to understand six months down the road.

相关文章