php PHP减去数组值

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/9118150/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-26 06:12:30  来源:igfitidea点击:

PHP subtract array values

phparraysnumbersintegersubtraction

提问by 19greg96

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?

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

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

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

$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.

我没有在这里添加一个键在一个数组中而不在另一个数组中的场合。

回答by rdlowrey

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

如果您愿意,您可以使用数组函数来避免 foreach。

The closure provided to array_mapdocsbelow will subtract each $arr1value from each corresponding $arr2. Unfortunately array_mapwon't preserve your keys when using more than one input array, so we use array_combinedocsto merge the subtracted results back into an array with the original keys:

提供到封闭array_map的文档文将减去每个$arr1从每个对应的值$arr2。不幸的是,array_map当使用多个输入数组时不会保留您的键,因此我们使用array_combinedocs将减去的结果合并回具有原始键的数组:

$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);

UPDATE

更新

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:

我对数组函数与简单 foreach 的方法比较感兴趣,所以我使用 Xdebug 对两者进行了基准测试。这是测试代码:

$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); }

As it turns out, using the foreachloop 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%.

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

enter image description here

在此处输入图片说明

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.

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

回答by Charles Forest

foreach ($arr2 as $key => $value) {
    if(array_key_exists($key, $arr1) && array_key_exists($key, $arr2))
        $ret[$key] = $arr2[$key] - $arr1[$key];
}

回答by siliconwafer

PHP does not offer vectorized mathematical operations. I would stick with your current approach of using a loop.

PHP 不提供矢量化数学运算。我会坚持你目前使用循环的方法。

First, I would get the set of array keys for each array. (See the array_keysfunction). Then, intersect them. Now you will have the keys common to each array. (Take a look at the array_intersectfunction). Finally, iterate. It's a readable and simple approach.

首先,我将获得每个数组的数组键集。(见array_keys函数)。然后,将它们相交。现在您将拥有每个数组共有的键。(看看array_intersect功能)。最后,迭代。这是一种可读且简单的方法。

Lastly, you could take a look at a library, such as Math_Vector: http://pear.php.net/package/Math_Vector

最后,您可以查看一个库,例如 Math_Vector:http://pear.php.net/package/Math_Vector