简体   繁体   中英

2d array - group by value and sum up same keys' values

Hello and thanks for taking the time to look at my question.

My current problem is that, I have the following array ( $topics_percentage ):

Array
(
    [0] => Array
        (
            [id] => 8989
            [cat] => Category 1
            [completed] => 0
        )

    [1] => Array
        (
            [id] => 8919
            [cat] => Category 2
            [completed] => 1
        )

    [2] => Array
        (
            [id] => 8913
            [cat] => Category 2
            [completed] => 1
        )

    [3] => Array
        (
            [id] => 8947
            [cat] => Category 1
            [completed] => 1
        )

    [4] => Array
        (
            [id] => 8949
            [cat] => Category 3
            [completed] => 1
        )

)

What I need to get, is something like the following example:

Array
(
    [Category 1] => Array
        (
            [noncompleted] => 1
            [completed] => 1
        )

    [Category 2] => Array
        (
            [completed] => 2
        )

    [Category 3] => Array
        (
            [completed] => 1
        )

)


What I've tried so far is this:

$class_array = [];

foreach ($topics_percentage as $v) {

    $complete = $v['completed'];

    $class_array[$v['cat']][] =
        ($complete == 0 ? 'noncompleted' : 'completed');
}

Which returns the following:

Array
(
    [Category 1] => Array
        (
            [0] => noncompleted
            [1] => completed
        )

    [Category 2] => Array
        (
            [0] => completed
            [1] => completed
        )

    [Category 3] => Array
        (
            [0] => completed
        )

)

I'm weak when it comes to arrays, and can't figure out the logic.

Thanks in advance.

Try this:

$values = array_unique(array_map(
    function ($v) { return $v['cat']; },
    $array
));

$result = array();
foreach ($values as $val) {
    $flt = array_filter($array, function ($v) use ($val) {
        return $v['cat'] == $val;
    });
    $cnt = count(array_filter($array, function ($v) use ($val) {
        return $v['completed'];
    }));
    $result[$val] = array(
        'completed' => $cnt,
        'noncompleted' => count($flt) - $cnt
    );
}

Try this:

    foreach ($topics_percentage as $v) {

        $complete = $v['completed'];

        if ($complete == 1) {
            $class_array[$v['cat']]['completed']++;
        } else {
            $class_array[$v['cat']]['uncompleted']++;
        }
    }

You should, of course, preinitialize the array before you count up values, but the basic idea is to use array cells as numeric values to be added or substracted from.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM