简体   繁体   中英

PHP - Split multidimensional array unique values

Think if I start with an explanation first it will help... I have a competition in which there are 3 winners in each County (The ones with the highest votes).

My current array looks like this:

Array
(
    [0] => Array
        (
            [entryID] => 1
            [votes] => 3
            [countyID] => 46
        )

    [1] => Array
        (
            [entryID] => 4
            [votes] => 1
            [countyID] => 2
        )

    [2] => Array
        (
            [entryID] => 2
            [votes] => 0
            [countyID] => 46
        )

    [3] => Array
        (
            [entryID] => 5
            [votes] => 0
            [countyID] => 46
        )

)

What I need to do here is figure out a way of finding the top 3 highest votes within each of the CountyID's.

Any ideas how I can achieve this? Thanks, Scott.

The simplest way to do it is to re-organize your array so the country id is the top level index, and then just write a simple custom function to sort the vote count in descending order... that way the top voted entries are on top.

$entries = array(
    array('entryId' => 1, 'votes' => 3, 'countryId' => 46),
    array('entryId' => 4, 'votes' => 1, 'countryId' => 2),
    array('entryId' => 2, 'votes' => 0, 'countryId' => 46),
    array('entryId' => 5, 'votes' => 0, 'countryId' => 46),
);

// Sort votes in descending order (most on top)
function voteSort($a, $b) {
    if ($a['votes'] == $b['votes']) {
        return 0;
    }
    return ($a['votes'] < $b['votes']) ? 1 : -1;
}

// Re-organize the array with country as top level
$byCountry = array();
foreach ($entries as $entry) {
    $byCountry[$entry['countryId']][] = array(
        'entryId' => $entry['entryId'],
        'votes'   => $entry['votes']
    );
}

// For each country, sort by votes
foreach ($byCountry as $index => $country) {
    usort($byCountry[$index], 'voteSort');
}

That should work.

The function ksort() will be helpful.
You can sort your array firstly with the rank and second the country. So you will have all of the firsts in every country on the begining of your array, then the seconds, etc.
The function you will pass to ksort will be kind of

function compareVote($a,$b){
  if($a['votes'] > $b['votes'])
    return 1;

  if($a['votes'] == $b['votes']){
    if($a['countyID'] > $b['countyID'])
      return 1;
    if($a['countyID'] == $b['countyID'])
      return 0;

    return -1;
  }

return -1;
}

View the official doc page .

You can split the array by unique country IDs in this way:

$entries = array(
 array('entryID' => 1, 'votes' => 3, 'countryID' => 46),
 array('entryID' => 4, 'votes' => 1, 'countryID' => 2),
 array('entryID' => 2, 'votes' => 0, 'countryID' => 46),
 array('entryID' => 5, 'votes' => 0, 'countryID' => 46),
);

$entriesByCountry = array();

foreach($entries as $entry) {
 if(!array_key_exists($entry->countyID, $entriesByCountry)
  $entriesByCountry[$entry->countyID] = array();

 $entriesByCountry[$entry->countyID][] = $entry;
}

Than sort each country-array by votes and take the first 3.

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