¿Cómo ordenar el hash de Perl en valores y ordenar las claves de manera correspondiente(quizás en dos matrices)?
sorting perl-hash (4)
Consulte la entrada de preguntas frecuentes de Perl titulada "Cómo ordenar un hash (opcionalmente por valor en lugar de por clave)"
http://perldoc.perl.org/perlfaq4.html#How-do-I-sort-a-hash-%28optionally-by-value-instead-of-key%29?
También puede usar perldoc -q
para buscar las Preguntas Frecuentes localmente en su máquina, como en perldoc -q sort
, que es como encontré su respuesta.
En Perl, quiero ordenar las claves de un hash por valor, numéricamente:
{
five => 5
ten => 10
one => 1
four => 4
}
produciendo dos matrices:
(1,4,5,10) and (one, four, five, ten)
Y luego quiero normalizar la matriz de valores de modo que los números sean secuenciales:
(1,2,3,4)
¿Cómo hago esto?
Primero ordena las claves por el valor asociado. A continuación, obtenga los valores (por ejemplo, utilizando una porción de hash).
my @keys = sort { $h{$a} <=> $h{$b} } keys(%h);
my @vals = @h{@keys};
O si tienes una referencia hash.
my @keys = sort { $h->{$a} <=> $h->{$b} } keys(%$h);
my @vals = @{$h}{@keys};
¿Cómo ordeno un hash (opcionalmente por valor en lugar de clave)?
Para ordenar un hash, comience con las teclas. En este ejemplo, le damos la lista de claves a la función de clasificación que luego las compara de forma ASCIIbética (que podría verse afectada por la configuración regional). La lista de salida tiene las claves en orden ASCIIbetical. Una vez que tengamos las claves, podemos revisarlas para crear un informe que muestre las claves en orden ASCIIbetical.
my @keys = sort { $a cmp $b } keys %hash;
foreach my $key ( @keys ) {
printf "%-20s %6d/n", $key, $hash{$key};
}
Podríamos ser más elegantes en el bloque sort () sin embargo. En lugar de comparar las claves, podemos calcular un valor con ellas y usar ese valor como comparación.
Por ejemplo, para hacer que nuestro orden de informes no distinga mayúsculas de minúsculas, usamos lc para minúsculas antes de compararlas:
my @keys = sort { lc $a cmp lc $b } keys %hash;
Nota: si el cálculo es costoso o el hash tiene muchos elementos, es posible que desee ver la Transformación de Schwartz para almacenar los resultados del cálculo.
Si queremos ordenar por el valor de hash, usamos la clave de hash para buscarlo. Todavía obtenemos una lista de claves, pero esta vez están ordenadas por su valor.
my @keys = sort { $hash{$a} <=> $hash{$b} } keys %hash;
A partir de ahí podemos llegar a ser más complejos. Si los valores de hash son los mismos, podemos proporcionar una clasificación secundaria en la clave de hash.
my @keys = sort {
$hash{$a} <=> $hash{$b}
or
"/L$a" cmp "/L$b"
} keys %hash;
my ( @nums, @words );
do { push @nums, shift @$_;
push @words, shift @$_;
}
foreach sort { $a->[0] <=> $b->[0] }
map { [ $h->{ $_ }, $_ ] } keys %$h
;