Hi rsiedl,

You say you want to find an "easier/quicker" way to find the highest value in a hash. Well, do you mean quicker to develop (less lines), or quicker to run (faster execution)? I'm assuming that "easier" means easier to read or understand?

Anyway, the quickest (both meanings) and easiest way is to just use the exact method you have already discared. Why? The sort built-in will always be the quickest sorting method for general numeric or string data, since it is a Perl built-in written directly in C, and is probably one of the most optimised Perl built-in functions (in fact, I wouldn't be surprised if my Benchmark timings below are inaccurate simply because of some optimisation or other I am unaware of). Also, the values function is the quickest way of getting at the values of a hash if you don't care about the keys. Combining sort and values is the quickest, and in my opinion, easiest way of achieving your objective.

my %hashName = ( "term1" => 83, "term2" => 20, "term3" => 193 ); my ($max) = sort { $b <=> $a } values %hashName;

This Benchmark script hopefully proves my point sufficiently well:

#!/usr/bin/perl use Benchmark qw(timethese cmpthese); my %hashName = ( "term1" => 83, "term2" => 20, "term3" => 193 ); print "Timings:\n\n"; my $r = timethese(1000000, { 'orig' => sub { my $i = 0; my $max = 0; foreach (sort sortHash (keys (%hashName))) { if ($i == 0) { $max = $hashName{$_}; last } } # end-foreach sub sortHash { $hashName{$b} <=> $hashName{$a}; } }, 'new' => sub { my ($max) = sort { $b <=> $a } values %hashName; }, }); print "\n\nComparison:\n\n"; cmpthese($r); __END__ Timings: Benchmark: timing 1000000 iterations of new, orig... new: 2 wallclock secs ( 2.44 usr + 0.00 sys = 2.44 CPU) @ 41 +0340.58/s (n=1000000) orig: 8 wallclock secs ( 8.42 usr + 0.00 sys = 8.42 CPU) @ 11 +8736.64/s (n=1000000) Comparison: Rate orig new orig 118737/s -- -71% new 410341/s 246% --

I hope that this helps. :-)

Update 31/05/2004: The Benchmark code I showed above seemed to be flawed. For some reason, using sub refs rather than eval strings seems to give better timings... the code was changed to reflect this.

Cheers,

-- Dave :-)


$q=[split+qr,,,q,~swmi,.$,],+s.$.Em~w^,,.,s,.,$&&$$q[pos],eg,print

In reply to Re: max value in a hash by DaveH
in thread max value in a hash by rsiedl

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.