2010-03-19 1 views
80

Ho il seguente structue di array:PHP Ordina array SubArray Valore

Array 
     (
      [0] => Array 
       (
        [configuration_id] => 10 
        [id] => 1 
        [optionNumber] => 3 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [1] => Array 
       (
        [configuration_id] => 9 
        [id] => 1 
        [optionNumber] => 2 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [2] => Array 
       (
        [configuration_id] => 8 
        [id] => 1 
        [optionNumber] => 1 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 
    ) 

Qual è il modo migliore per ordine la matrice, in modo incrementale sulla base del optionNumber?

Così i risultati assomigliano:

Array 
     (
      [0] => Array 
       (
        [configuration_id] => 8 
        [id] => 1 
        [optionNumber] => 1 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [1] => Array 
       (
        [configuration_id] => 9 
        [id] => 1 
        [optionNumber] => 2 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 

      [2] => Array 
       (
        [configuration_id] => 10 
        [id] => 1 
        [optionNumber] => 3 
        [optionActive] => 1 
        [lastUpdated] => 2010-03-17 15:44:12 
       ) 
    ) 

risposta

152

Usa usort.

function cmp_by_optionNumber($a, $b) { 
    return $a["optionNumber"] - $b["optionNumber"]; 
} 

... 

usort($array, "cmp_by_optionNumber"); 

In PHP ≥5.3, è necessario utilizzare un anonymous function invece:

usort($array, function ($a, $b) { 
    return $a['optionNumber'] - $b['optionNumber']; 
}); 

Si noti che sia il codice di cui sopra assumere $a['optionNumber'] è un intero. Utilizzare @St. John Johnson's solution se sono stringhe.


In PHP ≥7.0, utilizzare la spaceship operator <=> invece di sottrazione per evitare problemi di overflow/troncamento.

usort($array, function ($a, $b) { 
    return $a['optionNumber'] <=> $b['optionNumber']; 
}); 
+1

che in realtà non mi helpe come usort richiede fornisco una funzione da utilizzare - che è il po 'difficile non riesco a ottenere la mia testa rotonda – Sjwdavies

+11

Bene ha appena ti ha dato la funzione usare. E dovrai accettare che non sempre esiste una funzione incorporata per fare ciò che vuoi, devi scriverlo tu stesso. Le funzioni di confronto richiedono solo un ritorno di 1, 0 o -1 che indica l'ordinamento per due elementi. – Tesserex

+1

Ho guardato più in usort e in realtà è abbastanza bello. Ho scritto una funzione di comparazione semplice a quella precedente, ma ho saltato il '=='. Grazie per l'aiuto ragazzi – Sjwdavies

48

Uso usort

usort($array, 'sortByOption'); 
function sortByOption($a, $b) { 
    return strcmp($a['optionNumber'], $b['optionNumber']); 
} 
+0

Questo ha funzionato per me. @ KennyTM non sembra funzionare –

+7

@BenSinclair, questo perché la soluzione di Kenny è per i numeri, questa soluzione è per le stringhe. Sono entrambi corretti :-) +1 per questa alternativa. – kubilay

+0

Ha funzionato per me, perché stavo ordinando le stringhe ... – Andy

4

I tasti vengono rimossi quando si utilizza una funzione come quelli sopra. Se le chiavi sono importanti, la funzione seguente la manterrebbe ... ma i cicli foreach sono piuttosto inefficienti.

function subval_sort($a,$subkey) { 
    foreach($a as $k=>$v) { 
     $b[$k] = strtolower($v[$subkey]); 
    } 
    asort($b); 
    foreach($b as $key=>$val) { 
     $c[$key] = $a[$key]; 
    } 
    return $c; 
} 
$array = subval_sort($array,'optionNumber'); 

Utilizzare arsort invece di asort se si desidera da alto a basso.

credito

Codice: http://www.firsttube.com/read/sorting-a-multi-dimensional-array-with-php/

3

PHP 5.3+

usort($array, function($a,$b){ return $a['optionNumber']-$b['optionNumber'];}); 
11

ho usato entrambe le soluzioni da KennyTM e AJ Quick e si avvicinò con una funzione che può aiutare in questo problema per molti casi come utilizzando ASC o DESC ordinamento o conservazione chiavi o se si dispone di oggetti come figli di matrice.

Ecco questa funzione:

/** 
* @param array $array 
* @param string $value 
* @param bool $asc - ASC (true) or DESC (false) sorting 
* @param bool $preserveKeys 
* @return array 
* */ 
function sortBySubValue($array, $value, $asc = true, $preserveKeys = false) 
{ 
    if ($preserveKeys) { 
     $c = array(); 
     if (is_object(reset($array))) { 
      foreach ($array as $k => $v) { 
       $b[$k] = strtolower($v->$value); 
      } 
     } else { 
      foreach ($array as $k => $v) { 
       $b[$k] = strtolower($v[$value]); 
      } 
     } 
     $asc ? asort($b) : arsort($b); 
     foreach ($b as $k => $v) { 
      $c[$k] = $array[$k]; 
     } 
     $array = $c; 
    } else { 
     if (is_object(reset($array))) { 
      usort($array, function ($a, $b) use ($value, $asc) { 
       return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
      }); 
     } else { 
      usort($array, function ($a, $b) use ($value, $asc) { 
       return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
      }); 
     } 
    } 

    return $array; 
} 

Usage:

sortBySubValue($array, 'optionNumber', true, false); 

Modifica

La prima parte può essere riscritta utilizzando uasort() e il functi on sarà più breve:

/** 
* @param array $array 
* @param string $value 
* @param bool $asc - ASC (true) or DESC (false) sorting 
* @param bool $preserveKeys 
* @return array 
* */ 
function sortBySubValue($array, $value, $asc = true, $preserveKeys = false) 
{ 
    if (is_object(reset($array))) { 
     $preserveKeys ? uasort($array, function ($a, $b) use ($value, $asc) { 
      return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
     }) : usort($array, function ($a, $b) use ($value, $asc) { 
      return $a->{$value} == $b->{$value} ? 0 : ($a->{$value} - $b->{$value}) * ($asc ? 1 : -1); 
     }); 
    } else { 
     $preserveKeys ? uasort($array, function ($a, $b) use ($value, $asc) { 
      return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
     }) : usort($array, function ($a, $b) use ($value, $asc) { 
      return $a[$value] == $b[$value] ? 0 : ($a[$value] - $b[$value]) * ($asc ? 1 : -1); 
     }); 
    } 
    return $array; 
} 
+0

Questa è la migliore risposta più utile qui, dovrebbe essere in alto;) –

+0

@EdiBudimilic grazie, lo apprezzo! Tra l'altro ho aggiornato la mia risposta e aggiunto una versione più breve di questa funzione :) –

+1

Per far funzionare questo lavoro per me, ho dovuto usare '>' (maggiore di) invece di '-' (meno) confrontando' $ valori a' e '$ b' poiché stavo confrontando le stringhe. Funziona ancora però. – James