如果键不存在,如何合并数组并添加空元素

时间:2013-03-25 09:30:20

标签: php arrays merge

我有这3个阵列:

$a1 = array( 'a' => 1, 'b' => 2, 'c' => 3 );
$a2 = array( 'a' => 4, 'b' => 5, 'd' => 6 );
$a3 = array( 'a' => 7, 'c' => 8, 'd' => 9, 'x' => 10 );

我想合并它们,所以结果如下:

Array(
[a] => Array(
        [0] => 1
        [1] => 4
        [2] => 7
    )
[b] => Array(
        [0] => 2
        [1] => 5
        [2] => 
    )
[c] => Array(
        [0] => 3
        [1] => 
        [2] => 8
    )
[d] => Array(
        [0] => 
        [1] => 6
        [2] => 9
    )
[x] => Array(
        [0] => 
        [1] => 
        [2] => 10
    )

...我将在一个简单的表格中使用这些数据:

  col-1 col-2  col-3
a   1     4      7
b   2     5      -
c   3     -      8
d   -     6      9
x   -     -     10

array_merge_recursive很接近,但没有给我空元素,所以我相信我需要一个循环来完成工作。我的问题是弄清楚我需要在该循环中使用哪个函数。

我很乐意将两个数组一次合并为自定义用户函数。

6 个答案:

答案 0 :(得分:5)

我认为最简单的方法是从所有输入数组中获取所有键的列表,然后迭代键列表以构造结果数组:

$keys = array_unique(
    array_merge(
        array_keys($a1),
        array_keys($a2),
        array_keys($a3)
    )
);

$result = array();
foreach ($keys as $key) {
    $result[$key] = array(
        isset($a1[$key]) ? $a1[$key] : null,
        isset($a2[$key]) ? $a2[$key] : null,
        isset($a3[$key]) ? $a3[$key] : null
    );
}

print_r($result);

See it working

...或者如果你想提供一个具有任意数量输入数组的数组:

$keys = array();
foreach ($arrs as $arr) {
    $keys = array_merge($keys, array_keys($arr));
}
$keys = array_unique($keys);

$result = array();
foreach ($keys as $key) {
    $result[$key] = array();
    foreach ($arrs as $arr) {
        $result[$key][] = isset($arr[$key]) ? $arr[$key] : null;
    }
}

print_r($result);

See it working

答案 1 :(得分:4)

试试这个:

<?php
$a1    = array( 'a' => 1, 'b' => 2, 'c' => 3 );
$a2    = array( 'a' => 4, 'b' => 5, 'd' => 6 );
$a3    = array( 'a' => 7, 'c' => 8, 'd' => 9, 'x' => 10 );

$arr   = array($a1,$a2,$a3);
$cnt   = count($arr);

$res   = array();
foreach($arr as $key=>$val){
   foreach($val as $k=>$v){
     $res[$k][$key]  = $v;
   }
}
echo "<table>";
echo "<tr><td>&nbsp;</td><td>col-1</td><td>col-2</td><td>col-3</td></tr>";
foreach($res as $ky=>$vl){
   echo "<tr>";
   echo "<td>".$ky."</td>";
   for($i=0;$i<$cnt;$i++){
      if(array_key_exists($i,$vl)){
         echo "<td>".$vl[$i]."</td>";
      }
      else{
         echo "<td> - </td>";
      }
   }
   echo "</tr>";
}
echo "</table>";
?>

输出:

    col-1   col-2   col-3
a   1       4       7
b   2       5       -
c   3       -       8
d   -       6       9
x   -       -       10

答案 2 :(得分:3)

试试这个

<?php
 $a1 = array( 'a' => 1, 'b' => 2, 'c' => 3 );
 $a2 = array( 'a' => 4, 'b' => 5, 'd' => 6 );
$a3 = array( 'a' => 7, 'c' => 8, 'd' => 9, 'x' => 10 );
  function merge_common_keys(){
$arr = func_get_args();
$num = func_num_args();

$keys = array();
$i = 0;
for($i=0;$i<$num;++$i){
    $keys = array_merge($keys, array_keys($arr[$i]));
}
$keys = array_unique($keys);

$merged = array();

foreach($keys as $key){
    $merged[$key] = array();
    for($i=0;$i<$num;++$i){
        $merged[$key][] = isset($arr[$i][$key])?$arr[$i][$key]:null;
    }
}
  return $merged;
  }

$merged = merge_common_keys($a1,$a2,$a3);

print_r($merged);



$table = "<table>";




$table .= "<tr><td></td><td>col1</td><td>col2</td><td>col3</td></tr>";

foreach($merged as  $key=>$value)
  {
    $row = "<tr><td>$key</td>";
     foreach($value as $subvalue)
 {
   $row .= "<td>$subvalue</td>"; 
 }
 $table .= $row;
}
$table .= "</table>";
echo $table;
?>

参考:PHP, Merging arrays with common keys

查看实时演示http://codepad.viper-7.com/v8Ol5H

答案 3 :(得分:1)

您需要创建类似array_merge_recursive()的内容。

但是可能有一个更简单的解决方案,你说:

  

但不给我空元素,

但你确实知道它们不存在!

因此,如果您知道所需的最大列数(数组数量)并循环,那么您可以随时执行:

if(isset($row[$column])) {
   echo $row[$column];//your column
} else {
   echo 0;
}

答案 4 :(得分:1)

function myMergeFunction() {

  $my_new_array = array();

  $arg_list = func_get_args();
  for ($i = 0; $i < count($arg_list); $i++) {

    foreach($arg_list[$i] as $key => $value) {
      if(!is_array($my_new_array[$key]))
        $my_new_array[$key] = array();

      $my_new_array[$key][] = $value

    }

  }

  return $my_new_array;

}
你可以这样称呼它:

myMergeFunction($a, $b, $c, $d, [...]);

答案 5 :(得分:1)

→在有任何答案之前已经开始了这个问题,即使已经有了可以接受的答案,也决定完成它。这个版本更具动态性,并且对表的样式进行了一些自定义:

代码:

/* Arrays from Question */  $a1 = array( 'a' => 1, 'b' => 2, 'c' => 3 ); $a2 = array( 'a' => 4, 'b' => 5, 'd' => 6 ); $a3 = array( 'a' => 7, 'c' => 8, 'd' => 9, 'x' => 10 );
/* Process Arrays       */  $result = handle_arrays( $a1, $a2, $a3 );
/* Create & Echo Table  */  echo ( array_table( $result ) );

function handle_arrays() {
    /* Get Arrays    */  $params = func_get_args(); $result = array();
    /* Merge Arrays  */  foreach( $params as $k=>$v ) { foreach( $v as $key=>$val ) { if( !array_key_exists( $key, $result ) ) $result[ $key ] = array(); $result[ $key ][ $k ] = $val; } }
    /* Handle Blanks */  for( $x = 0; $x < func_num_args(); $x++ ) { foreach( $result as $key=>$val ) { if( !array_key_exists( $x, $val ) ) { $result[ $key ][ $x ] = '-'; } ksort( $result[ $key ] ); } }
    /* Return Array  */  $return = array( func_num_args(), $result );
    return( $return );
}
function array_table( $array ) {
    /* Array # & Result Array */  $n = $array[ 0 ]; $a = $array[ 1 ];
    /* Style & Class Control  */  $padding_left = 10; $padding_right = 10; $col_align = "center"; $key_align = "left"; $table_class = ""; $col_class = ""; $row_class = ""; $field_class = "";
    /* Table & Column Headers */  $html = "<table class='{$table_class}'><tr><td style='padding-right:{$padding_right}px'></td>"; for( $x=0; $x<$n; $x++ ) { $html .= "<td style='padding-left:{$padding_left}px;padding-right:{$padding_right}px' class='{$col_class}'>col-$x</td>"; } $html .= "</tr>";
    /* Row and Fields Values  */  foreach( $a as $key=>$val ) { $html .= "<tr><td align='{$key_align}' class='{$row_class}'>$key</td>"; foreach( $val as $k=>$v ) { $html .= "<td align='{$col_align}' class='{$field_class}'>$v</td>"; } $html .= "</tr>"; } $html .= "</table>";
    return( $html );
}

输出:

    col-0   col-1   col-2
a     1       4       7
b     2       5       -
c     3       -       8
d     -       6       9
x     -       -       10