如何在php中合并两个关联数组,使我们不会在所有情况下覆盖任何重复的条目?

时间:2021-12-28 21:37:40

I have two associative array which have many content same and so I want to combine those two arrays in such a way that if I have a in array 1 and a in array 2 than in array 3 I should have entries for both a's and not 1.

我有两个有很多内容相同的关联数组所以我想把这两个数组组合起来如果我有一个在数组1中,另一个在数组2中,而不是在数组3中我应该有两个a的元素而不是1。

I have tried using array_merge but it would overwrite entries in 1st array if there are any duplicates in 2nd array, I have also tried using + but it gives me fatal error saying Fatal error: Unsupported operand types in /home/code.php then I tried doing

我尝试过使用array_merge,但如果在第2个数组中有重复,它会覆盖第1个数组中的条目,我也尝试过使用+,但它会给我致命的错误,说致命错误:/home/ codein中不支持操作数类型。然后我尝试了php

(array)$ar3 = (array)$ar1 +(array)$ar2 and it seems to add up. I want to know is this the correct way to do it and also why did initially I got fatal error and than it worked as I had already defined $ar3, $ar2, $ar1 as array types.

(数组)$ar3 =(数组)$ar1 +(数组)我想知道这是正确的方法吗?为什么一开始我有致命错误,而且比它有用,因为我已经将$ar3 $ar2 $ar1定义为数组类型。

$orders = new Order(); 
$prospectOffers = $orders->getOrder($orderConfNumber); 
$prospectOffersResult = json_decode($prospectOffers,true); 
$shoppingBasket = $cart->getCartItems(); 
var_dump($prospectOffersResult); // Both are arrays 
var_dump($shoppingBasket); //Both are arrays 
(array)$result = (array)$prospectOffersResult+(array)$shoppingBasket;

Thanks.

谢谢。

2 个解决方案

#1


14  

$array1 + $array2 will return the union of the two arrays. If they are associative, values from the left operand will be preferred if keys collide. Therefore, this is not the solution you want as values will be lost.

$array1 + $array2将返回两个数组的联合。如果它们是关联的,则从左操作数的值,如果键发生冲突,则首选。因此,这不是您想要的解决方案,因为值将丢失。

There is nothing wrong with the statement provided both variables are understood as arrays. Your fatal error likely occurred because one variable was actually an object, and it's possible to mistake that using var_dump. By adding the type casts you forced PHP to coerce both variables to arrays. If one variable was an object, it would have this effect:

只要将两个变量都理解为数组,语句就没有问题。您可能会发生致命错误,因为一个变量实际上是一个对象,并且可能会错误地使用var_dump。通过添加类型强制PHP将两个变量强制到数组中。如果一个变量是一个对象,它会产生以下效果:

From the PHP.net Manual

从PHP.net手册

"If an object is converted to an array, the result is an array whose elements are the object's properties. The keys are the member variable names, with a few notable exceptions: integer properties are unaccessible; private variables have the class name prepended to the variable name; protected variables have a '*' prepended to the variable name. These prepended values have null bytes on either side."

如果一个对象被转换成一个数组,那么结果就是一个数组,其元素是对象的属性。键是成员变量名,有几个显著的例外:整数属性是不可访问的;私有变量将类名预先写在变量名之前;受保护的变量对变量名有“*”前缀。这些前缀的值在任何一侧都有null字节。

Now having two arrays to add, PHP had nothing to panic about. Note that while casting the two operands of + was important, it was meaningless to cast the variable you were assigning to. The expression (array)$foo does not modify $foo, but rather returns a new value. This may not be intuitive from languages that require you to declare variables, but PHP is not such a language.

现在有两个数组要添加,PHP没有什么好担心的。注意,虽然强制执行+的两个操作数很重要,但是强制执行要分配给的变量是没有意义的。表达式(数组)$foo不修改$foo,而是返回一个新值。这对于需要声明变量的语言来说可能不是很直观,但是PHP不是这样的语言。

On your other issue, you cannot have two of the same key in an array. This would make it impossible to index the array as the correct value to return would become ambiguous. If you wish to combine two arrays in a lossless manor, you will have to use a more complicated data structure.

在另一个问题中,数组中不能有两个相同的键。这将使索引数组成为不可能的,因为返回的正确值将变得不明确。如果您希望将两个数组合并到一个无损的manor中,则必须使用更复杂的数据结构。

My suggestion is to use an array of arrays, where:

我的建议是使用数组,其中:

$a1 = array('a' => 1, 'b' => 2, 'c' => 3);
$a2 = array('a' => 3, 'b' => 2, 'd' => 2);

Will become:

将成为:

$a3 = array(
    'a' => array(1, 3),
    'b' => array(2, 2),
    'c' => array(3),
    'd' => array(2)
);

And the ordering is not determined. The only notable change to the structure is that all first values are arrays, allowing values of duplicate keys to be accumulated. This function does the task and might do with a better name:

而且顺序也不确定。该结构唯一值得注意的变化是,所有第一个值都是数组,允许累积重复键的值。这个函数可以完成这个任务,并且可以使用更好的名称:

// array(array) lossless_array_merge([$array1 [, $array2 [, $...]]])

function lossless_array_merge() {
  $arrays = func_get_args();
  $data = array();
  foreach ($arrays as $a) {
    foreach ($a as $k => $v) {
      $data[$k][] = $v;
    }
  }
  return $data;
}

#2


1  

array_merge() will override duplicates only if both arrays contain the same string keys:

只有当两个数组包含相同的字符串键时,array_merge()才会重写副本:

If the input arrays have the same string keys, then the later value for that key will overwrite the previous one. If, however, the arrays contain numeric keys, the later value will not overwrite the original value, but will be appended.

如果输入数组具有相同的字符串键,那么该键的后一个值将覆盖前一个键。但是,如果数组包含数字键,则后面的值将不会覆盖原始值,而是将被追加。

I believe this behavior is expected. How would you handle this case? Let's say that

我相信这种行为是意料之中的。你将如何处理这个案子?假设

$arr1 = array('a' => 1);
$arr2 = array('a' => 2);

What would be an acceptable output after the array merge?

什么是数组合并后可接受的输出?

#1


14  

$array1 + $array2 will return the union of the two arrays. If they are associative, values from the left operand will be preferred if keys collide. Therefore, this is not the solution you want as values will be lost.

$array1 + $array2将返回两个数组的联合。如果它们是关联的,则从左操作数的值,如果键发生冲突,则首选。因此,这不是您想要的解决方案,因为值将丢失。

There is nothing wrong with the statement provided both variables are understood as arrays. Your fatal error likely occurred because one variable was actually an object, and it's possible to mistake that using var_dump. By adding the type casts you forced PHP to coerce both variables to arrays. If one variable was an object, it would have this effect:

只要将两个变量都理解为数组,语句就没有问题。您可能会发生致命错误,因为一个变量实际上是一个对象,并且可能会错误地使用var_dump。通过添加类型强制PHP将两个变量强制到数组中。如果一个变量是一个对象,它会产生以下效果:

From the PHP.net Manual

从PHP.net手册

"If an object is converted to an array, the result is an array whose elements are the object's properties. The keys are the member variable names, with a few notable exceptions: integer properties are unaccessible; private variables have the class name prepended to the variable name; protected variables have a '*' prepended to the variable name. These prepended values have null bytes on either side."

如果一个对象被转换成一个数组,那么结果就是一个数组,其元素是对象的属性。键是成员变量名,有几个显著的例外:整数属性是不可访问的;私有变量将类名预先写在变量名之前;受保护的变量对变量名有“*”前缀。这些前缀的值在任何一侧都有null字节。

Now having two arrays to add, PHP had nothing to panic about. Note that while casting the two operands of + was important, it was meaningless to cast the variable you were assigning to. The expression (array)$foo does not modify $foo, but rather returns a new value. This may not be intuitive from languages that require you to declare variables, but PHP is not such a language.

现在有两个数组要添加,PHP没有什么好担心的。注意,虽然强制执行+的两个操作数很重要,但是强制执行要分配给的变量是没有意义的。表达式(数组)$foo不修改$foo,而是返回一个新值。这对于需要声明变量的语言来说可能不是很直观,但是PHP不是这样的语言。

On your other issue, you cannot have two of the same key in an array. This would make it impossible to index the array as the correct value to return would become ambiguous. If you wish to combine two arrays in a lossless manor, you will have to use a more complicated data structure.

在另一个问题中,数组中不能有两个相同的键。这将使索引数组成为不可能的,因为返回的正确值将变得不明确。如果您希望将两个数组合并到一个无损的manor中,则必须使用更复杂的数据结构。

My suggestion is to use an array of arrays, where:

我的建议是使用数组,其中:

$a1 = array('a' => 1, 'b' => 2, 'c' => 3);
$a2 = array('a' => 3, 'b' => 2, 'd' => 2);

Will become:

将成为:

$a3 = array(
    'a' => array(1, 3),
    'b' => array(2, 2),
    'c' => array(3),
    'd' => array(2)
);

And the ordering is not determined. The only notable change to the structure is that all first values are arrays, allowing values of duplicate keys to be accumulated. This function does the task and might do with a better name:

而且顺序也不确定。该结构唯一值得注意的变化是,所有第一个值都是数组,允许累积重复键的值。这个函数可以完成这个任务,并且可以使用更好的名称:

// array(array) lossless_array_merge([$array1 [, $array2 [, $...]]])

function lossless_array_merge() {
  $arrays = func_get_args();
  $data = array();
  foreach ($arrays as $a) {
    foreach ($a as $k => $v) {
      $data[$k][] = $v;
    }
  }
  return $data;
}

#2


1  

array_merge() will override duplicates only if both arrays contain the same string keys:

只有当两个数组包含相同的字符串键时,array_merge()才会重写副本:

If the input arrays have the same string keys, then the later value for that key will overwrite the previous one. If, however, the arrays contain numeric keys, the later value will not overwrite the original value, but will be appended.

如果输入数组具有相同的字符串键,那么该键的后一个值将覆盖前一个键。但是,如果数组包含数字键,则后面的值将不会覆盖原始值,而是将被追加。

I believe this behavior is expected. How would you handle this case? Let's say that

我相信这种行为是意料之中的。你将如何处理这个案子?假设

$arr1 = array('a' => 1);
$arr2 = array('a' => 2);

What would be an acceptable output after the array merge?

什么是数组合并后可接受的输出?