phparraysmultidimensional-arraymappinggrouping

Filter and group data from a 2d array according to a 2d whitelist/mapping array


I'm trying to achieve proper merging of two 2d arrays.

$year = [
    ['name' => '2020'],
    ['name' => '2019'],
    ['name' => '2018'],
    ['name' => '2017']
];

$meeting = [
    ['name' => 'meeting1', 'year' => '2020'],
    ['name' => 'meeting2', 'year' => '2020'],
    ['name' => 'meeting3', 'year' => '2019'],
    ['name' => 'meeting4', 'year' => '2018'],
    ['name' => 'meeting5', 'year' => '2018'],
];

The result I desire would look like this:

[
    0 => [
        '2020' => [
            0 => ['name' => 'meeting1'],
            1 => ['name' => 'meeting2']
        ]
    ],
    1 => [
        '2019' => [
            0 => ['name' => 'meeting3']
        ]
    ],
    2 => [
        '2018' => [
            0 => ['name' => 'meeting4'],
            1 => ['name' => 'meeting5']
        ]
    ],
    3 => [
        '2017' => []
    ]
]

However both "+" operator and array_merge() used on $meeting and $year are producing different results than what I require. Is it possible to do using + operator or array_merge or am I required to use foreach loops?


Solution

  • There is no PHP native function for group array but as said, simple for loop should do it:

    foreach($meeting as $e) {
        $array[$e['year']][] = array('name' => $e['name']);
    }
    

    And $array will you have you desire result.

    Live example: 3v4l

    Edit

    If you want all the years from $year just init before as:

    foreach($year as $e)
        $array[$e['name']] = [];
    

    And then use the first for loop

    So full solution will be:

    foreach($year as $e)
        $array[$e['name']] = [];
    foreach($meeting as $e)
        $array[$e['year']][] = array('name' => $e['name']);
    

    Output:

    array (
      2020 => 
      array (
        0 => 
        array (
          'name' => 'meeting1',
        ),
        1 => 
        array (
          'name' => 'meeting2',
        ),
      ),
      2019 => 
      array (
        0 => 
        array (
          'name' => 'meeting3',
        ),
      ),
      2018 => 
      array (
        0 => 
        array (
          'name' => 'meeting4',
        ),
        1 => 
        array (
          'name' => 'meeting5',
        ),
      ),
      2017 => 
      array (
      ),
    )