简体   繁体   English

按值分组php数组

[英]Grouping php array by value

I have an array pulled back from a database that is ordered by number ([0]=>'',[1]=>''...etc) within each element there are various associative values (title,date,area...etc). 我有一个数组从数据库中拉回来的数字([0]=>'',[1]=>''...etc)在每个元素中有各种关联值(标题,日期,区域。 ..等等)。 I need the array reordering so that all the elements with the same 'area' variable appear together. 我需要重新排序数组,以便所有具有相同“area”变量的元素一起出现。 So effectively we will still have a ([0]=>'',[1]=>''...etc) array but the first 5 or so will have the same 'area' then the next however many will have the same 'area' and so on. 所以有效地我们仍然会有一个([0]=>'',[1]=>''...etc)数组但是前5个左右会有相同的'区域'然后下一个然后很多会有相同的“区域”等。

To make it easier there are 4 possible values for the 'area' field (north,west,central,blyth valley). 为了方便起见,“区域”字段(北部,西部,中部,blyth山谷)有4个可能的值。

What I dont want is a multi-dimensional array grouped by the 4 areas, I need it as one long array just in the order that puts all 'like' areas together. 我不想要的是一个按4个区域分组的多维数组,我需要它作为一个长数组,只是按顺序将所有“相似”区域放在一起。

Not sure if I've explained this as well as I possibly could but any help appreciated. 我不确定我是否已尽可能地解释这一点,但任何帮助表示赞赏。 If you need me to clear anything up just reply and I'll add appropriately. 如果你需要我清除任何东西,只需回复,我会适当添加。

Simply sort the array using a custom sort function with usort if you're unable to ORDER BY the field in SQL. 如果您无法在SQL中按字段顺序排序,只需使用自定义排序函数对数组进行排序。 Shouldn't be too much of a performance hit anyway, depending on the number of entries you have in the array. 不管怎样,不应该过多地影响性能,具体取决于阵列中的条目数量。

usort($posts, function ($a, $b) { return strcmp($a['area'], $b['area']); });

If you want a predetermined sort order, add a list of the different areas and their priorities: 如果您想要预定的排序顺序,请添加不同区域及其优先级的列表:

$sortOrder = array(
    'north' => 100,
    'west' => 200,
    'central' => 300,
    'blyth valley' => 400,
);

usort($posts, function ($a, $b) use ($sortOrder) {
    if (isset($sortOrder[$a['area']], $sortOrder[$b['area']]))
    {
        return $b['area'] - $a['area'];
    }

    if (isset($sortOrder[$a['area']]))
    {
        return -1;
    }

    if (isset($sortOrder[$b['area']]))
    {
        return 1;
    }

    return 0;
});

You can remove the tests if you have a priority defined for all possible values of the 'area' field, although I'd suggest leaving it in since you'll probably be changing the possible values in the future. 如果您为“区域”字段的所有可能值定义了优先级,则可以删除测试,但我建议将其保留,因为您可能会在将来更改可能的值。

Here is a solution... 这是一个解决方案......

$arr = array(
    '0' => array( 'area' => 'west' ),
    '2' => array( 'area' => 'north' ),
    '3' => array( 'area' => 'west' ),
    '4' => array( 'area' => 'central' ),
    '5' => array( 'area' => 'west' ),
    '6' => array( 'area' => 'north' )
);

$new = array();

// Get a list of possible areas
$areas = array();
foreach ($arr as $key => $value) {
    if ( ! in_array( $value['area'] , $areas ) ) {
        array_push( $areas, $value['area'] );
    }
}

// For each area...
foreach ($areas as $key => $area) {
    // Find a area that matches...
    foreach ($arr as $key => $value) {
        if ( $value['area'] == $area ) {
            array_push( $new, $value );
        }
    }
}

Also you may want to remove the first loop if there are only a set number of areas. 如果只有一定数量的区域,您可能还想删除第一个循环。 Just fill the areas array with a list of possible areas in the order you want. 只需按所需顺序填充区域数组中的可能区域列表即可。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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