Newsgroup: it.comp.www.php
Titolo: Ordinare una matrice

Ho cercato molto su stackoverflow ma non sono riuscito a trovare la
risposta.
 
Ho una matrice, un array bidimensionale nxm e vorrei ordinarlo per
colonne con priorità prima alla prima colonna, poi alla seconda colonna,
alla terza, ecc, ecc.
 
Mi spiego meglio con un esempio (tra parentesi l'ordine che vorrei):
 
3 2 1 0 ...(7)
5 3 9 5 ...(3)
5 1 2 3 ...(4)
4 5 6 7 ...(5)
5 6 9 8 ...(1)
5 6 8 1 ...(2)
4 4 9 6 ...(6)
2 5 8 4 ...(8)
 
Vorrei ordinarla in questo modo:
 
5 6 9 8
5 6 8 1
5 3 9 5
5 1 2 3
4 5 6 7
4 4 9 6
3 2 1 0
2 5 8 4
 
Come si vede è una cosa piuttosto semplice ma vorrei farlo con le
funzioni predefinite ovvero con array_multisort che dovrebbe servire per
ordinare gli array multidimensionali.
 
$arr_key = array_keys($matrix[0]);
array_multisort($matrix[0], $matrix[1], .., $matrix[n],$arr_key);
 
C'è la possibilità oppure occorre rivolgersi a usort?
 
Una idea che mi viene è quella di usare un artificio matematico ovvero
$base = max(max($matrix);
3 2 1 0 si trasforma nel numero $num[0] = 3 + 2 *$base + 1 *$base*$base
+ 0 *$base*$base*$base
 
e così via per tutte le righe di matrix. Poi questi numeri contenuti nel
vettore $num si usano per ordinare la matrice dalla prima riga
all'ultima con un:
 
$arr_key = array_keys($num);
array_multisort($num,$arr_key);
 
$arr_key da appunto l'ordine corretto delle righe di $matrix ordinate
ovvero $arr_key[0] == 4 .. $arr_key[7) == 7.
 
Il problema di questo approccio è che i numeri possono essere molto
grandi e anche andare in overflow.
 
-- 
Sandro kensan 
www.kensan.it
 & 
www.qiqi.it
 geek site
Saluto gli agenti della NSA - Hello NSA - 
www.nsa.gov
 

2 5 8 4 ...(8)
 
Piu' semplice di quel che credi, se i tipi di dato sono comparabili.
 
	rsort($matrix);
 
Se i numeri sono molto grandi, puoi convertirli in stringhe di uguale
lunghezza con sprintf:	17 => "00000000000000017". Un po' brutale, ma
dovrebbe funzionare. Ma non vedo perche' dovrebbe essere necessario?
 
Leonardo
 
-- 
 
Enough, enough!  But, stranger, ere we part,
Glancing farewell to each nefarious bier,
This warning would I beg you take to heart:
There is an end to e'en the worst career!

	rsort($matrix);
 
Stupido test:
 
<?php
    $matrix = [
        [ 3, 2, 1, 0, "(7)" ],
        [ 5, 3, 9, 5, "(3)" ],
        [ 5, 1, 2, 3, "(4)" ],
        [ 4, 5, 6, 7, "(5)" ],
        [ 5, 6, 9, 8, "(1)" ],
        [ 5, 6, 8, 1, "(2)" ],
        [ 4, 4, 9, 6, "(6)" ],
        [ 2, 5, 8, 4, "(8)" ],
    ];
 
    rsort($matrix);
 
    print implode("\n", array_map(function($v) { return implode(", ", $v); },
$matrix)) . "\n";
 
 
"order.php" 15L, 395C written
mintaka:~ $ php -q order.php
5, 6, 9, 8, (1)
5, 6, 8, 1, (2)
5, 3, 9, 5, (3)
5, 1, 2, 3, (4)
4, 5, 6, 7, (5)
4, 4, 9, 6, (6)
3, 2, 1, 0, (7)
2, 5, 8, 4, (8)
mintaka:~ $


 
 
Grazie Leonardo ma questa caratteristica non è descritta nel manuale. Il
che mi sta spiazzando, possibile che una cosa così semplice non sia
descritta chiaramente? Forse sono io che sono tonto...
 
Grazie di nuovo. Io intanto stavo facendo una funzione ricorsiva che
ordinasse richiamando array_multisort, funzione inutile a questo punto.
 
Buona natte.


descritta chiaramente?
 
Effettivamente emerge dal combinato disposto di tre diverse pagine, e, ora
che mi ci fai pensare, non viene mai detto da nessuna parte che sia questo
il comportamento DEFINITO - discende solo dal fatto che Array supporta una
metrica lessicografica basata sui valori degli elementi.
 
Come dire, nessuno mi garantisce (non che me lo garantirebbe comunque...!)
che nel PHP 5.7 o 6.0 questa soluzione smetta di funzionare.
 
Cio' mi inquieta & irrita anzicheno'.
 
D'altra parte, osservando i sorgenti e ponzandoci su, credo che sarebbe un
bagno di sangue peggiore CAMBIARE il comportamento piuttosto che mantenere
tutto come sta, quindi io starei abbastanza tranquillo.
 
Ugualmente penso che in quei due, tre punti dove mi sono avvalso di questo
trucco aggiungero' un commento e un "sanity unit test".
 
Leonardo


 trucco aggiungero' un commento e un "sanity unit test".
 
Se non lo fai tu che sei esperto lo faccio io:
http://php.net/manual/en/function.rsort.php
 
un bell'esempio in cui una matrice viene ordinata, tale e quale quello
discusso in questo topic.
 
Se l'avessi trovato non avrei chiesto qui.
