Beefy Boxes and Bandwidth Generously Provided by pair Networks
There's more than one way to do things

Sort a long list of hosts by domain (code)

by deprecated (Priest)
on Jun 23, 2001 at 19:57 UTC ( #90970=snippet: print w/replies, xml ) Need Help??
Description: I log all incoming connections to my opennap server to a postgres database. I get about 625,000 connections per day, and I wanted to sort them by domain so that I could see visually in text where they were coming from. So I'll spare you the database calls. This, however, was a cool little hack to print the hosts out sorted by domain (rather than hostname). You can easily use File::Slurp to write the scalar obtained.

Credit to risacher for the sprintf right-justify.

my $noodle = join "$/", map { sprintf "%64s", $_ } ( sort { reverse($a
+) cmp reverse($b) } (keys %hosts) );
Replies are listed 'Best First'.
Re: Sort a long list of hosts by domain
by japhy (Canon) on Jun 23, 2001 at 20:42 UTC
    I have a feeling this has a speed increase. It's a Guttman-Rosler Transform, which means that the sorting is done by the native sort(). Also, I only reverse each key twice, whereas your method is probably doing a lot more reversing.
    @by_domain = map { scalar reverse } sort map { scalar reverse } keys %hosts;

    japhy -- Perl and Regex Hacker
      How about a pointer to Guttman-Rosler Transform, or a list of such transforms in general? I assume this will be in your book?
        My book is regex-related. Uri Guttman and/or Larry Rosler has information about the GRT; try this URL. I do have some sorting stuff online at my web site.

        japhy -- Perl and Regex Hacker
Re: Sort a long list of hosts by domain
by Brovnik (Hermit) on Jun 24, 2001 at 00:18 UTC
    This is perfect for the Schwartzian Transform.
    my @sorted = map { $_->[1] } sort { $a->[0] cmp $b->[0] } map { [join('.',reverse split(/\./)),$_] } @unsorted;
    or, to put it into the form you provided,
    my $noodle = join($/, map { sprintf("%64s",$_->[1]) } sort { $a->[0] cmp $b->[0] } map { [join('.',reverse split(/\./)),$_] } keys %hash );
    Update: to point to merlyn's original post.
Re: Sort a long list of hosts by domain
by mdillon (Priest) on Jun 23, 2001 at 21:18 UTC
    i'm not sure i agree that you are sorting by domain. domains are grouped, but the overall order of the result is strange. however, i think the following sub does what most people would expect:
    sub sort_domains { map { ${$_->[0]} } sort { my ($pa, $pb, $rv) = ($#{$a->[1]}, $#{$b->[1]}, 0); do { $rv ||= $a->[1][$pa] cmp $b->[1][$pb] } while (!$rv and $pa-- and $pb--); $rv ||= ($pb >= 0) ? -1 : ($pa >= 0) ? 1 : 0; } map { [ \$_, [ split /\./, $_ ] ] } @_ }
    you can use it like so: my $noodle = join $/, map { sprintf "%64s", $_ } sort_domains keys %hosts;

    p.s. let the golf begin

    p.p.s. why $noodle?

    update: fixed logic bug in line that deals with extra domain parts ($rv ||= ($pb >= 0) ? -1…)

Log In?

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: snippet [id://90970]
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others contemplating the Monastery: (3)
As of 2023-12-10 14:40 GMT
Find Nodes?
    Voting Booth?
    What's your preferred 'use VERSION' for new CPAN modules in 2023?

    Results (40 votes). Check out past polls.