Beefy Boxes and Bandwidth Generously Provided by pair Networks
good chemistry is complicated,
and a little bit messy -LW
 
PerlMonks  

Re^2: Sorting hash

by bartrad (Beadle)
on Apr 05, 2018 at 18:39 UTC ( #1212368=note: print w/replies, xml ) Need Help??


in reply to Re: Sorting hash
in thread Sorting hash

Hi, thanks for the reply. Sorry, I redacted the data where hostname sat. Those values are in fact unique for each key.

'hostname1' => { '1' => { 'pass' => 1, 'cpu' => '0.1 +1%', 'box_name' => + '', 'capacity' => + '0.57%' } }, 'hostname2' => { '1' => { 'pass' => +1, 'cpu' => ' +0.09%', 'box_name' + => '', 'capacity' + => '0.43%' } },

Replies are listed 'Best First'.
Re^3: Sorting hash
by ablanke (Vicar) on Apr 05, 2018 at 19:01 UTC

    Hi,

    there you go.

    i must confess that i missed also 1 thing in your sort function.

    the cpu percentage will not interpreted as an numeric value, so you have to use cmp instead of <=>.

    see perlop

    #!/usr/bin/perl use strict; use warnings; use Data::Dumper; my %results = ( 'hostname1' => { '1' => { 'pass' => 1, 'cpu' => '0.07%', 'box_name' => 'hostname', 'capacity' => '0.41%' } }, 'hostname2' => { '1' => { 'pass' => 1, 'cpu' => '0.04%', 'box_name' => 'hostname', 'capacity' => '0.25%' } } ); my $results = \%results; foreach my $router ( sort { $results->{$a}{1}{cpu} cmp $results->{$b}{ +1}{cpu} } keys %{results} ) { print Dumper($results->{$router}); }
      the cpu percentage will not interpreted as an numeric value

      Actually, due to Perl trying to numberify a string in numeric context, it turns out percents written as strings get reasonably interpreted as numbers:

      C:\WINDOWS\system32>perl -MDevel::Peek=Dump -le " $a = qq(3.14%); Dump + $a; $b = qq(2.718%); Dump $b; print $a <=> $b; Dump $a; Dump $b" SV = PV(0x1daf58) at 0x44d2660 REFCNT = 1 FLAGS = (POK,IsCOW,pPOK) PV = 0x44ebf28 "3.14%"\0 CUR = 5 LEN = 10 COW_REFCNT = 1 SV = PV(0x1dafb8) at 0x44d2300 REFCNT = 1 FLAGS = (POK,IsCOW,pPOK) PV = 0x44ebe68 "2.718%"\0 CUR = 6 LEN = 10 COW_REFCNT = 1 1 SV = PVNV(0x1d9288) at 0x44d2660 REFCNT = 1 FLAGS = (POK,IsCOW,pNOK,pPOK) IV = 0 NV = 3.14 PV = 0x44ebf28 "3.14%"\0 CUR = 5 LEN = 10 COW_REFCNT = 1 SV = PVNV(0x1d9268) at 0x44d2300 REFCNT = 1 FLAGS = (POK,IsCOW,pIOK,pNOK,pPOK) IV = 2 NV = 2.718 PV = 0x44ebe68 "2.718%"\0 CUR = 6 LEN = 10 COW_REFCNT = 1
      ... They start out as just the string (PV); but after running numeric compare, you can see that it had the right output value for $a <=> $b (1) and afterward, they also have the reasonable floating-point value (NV) of 3.14 and 2.718.

        Hi,

        you are right, but you get an warning:

        Argument "0.04%" isn't numeric in numeric comparison (<=>)

        the sorting order, in this trivial example, is the same, but who knows what shows up in the real world.

        so a numeric compare seems to be the more obvious choice in this case.

        of course there are several ways to get rid of the warnings and using numeric comparison.

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: note [id://1212368]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others scrutinizing the Monastery: (3)
As of 2020-07-05 09:42 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found

    Notices?