Anonymous Monk has asked for the wisdom of the Perl Monks concerning the following question:

I want to set up a feature on my site where users see a list, like the top 10 best selling songs, and then vote themselves. The 'original' Top 10 and the visitors Top 10 will be displayed side-by-side.

This is best illustrated with an example:

Chart Position      Visitor Position   Song
-------------------------------------------------------
1                   10                 Insomnia
2                   1                  Enter Sandman
3                   2                  Bad Moon Rising
4                   5                  Sunchyme
5                   3                  Beautiful Stranger
6                   4                  One
7                   6                  Wild Thing
8                   9                  Answer the Phone
9                   7                  Feel It
10                  8                  Can't get enough...
So, visitors to the site vote for their favourite song by selecting it from a menu somewhere. I can't believe this simple thing is so difficult to code.

I have a plain text file for each song which contains the 'fixed position', i.e. the chart position, and the current visitors' position. When a user votes, the relevant file is opened, and the visitor position incremented.

I've tried using different arrays, but I can't sort them both in the same way as they get "out of sync". So I tried using a hash like $song{$chart_position}{$name}, but I couldn't figure the sorting out. (It should be in order of the chart position).

I'm really going mad trying to figure this out, so I'd appreciate any help.

(Please do not suggest using a database or something, I just really want to keep this simple)

  • Comment on Fixed 'Top 10' compared with visitors' Top 10

Replies are listed 'Best First'.
Re: Fixed 'Top 10' compared with visitors' Top 10
by mikfire (Deacon) on May 26, 2000 at 23:27 UTC
    You had the right idea with the hashes. I personally would code it using a hash kind of like this:
    $song{$chart_position}{TITLE} = 'Insomnia'; $song{$chart_position}{VISITOR_POS} = 10;
    then, to sort by chart position:
    for $pos ( sort { $a <=> $b } keys %song ) { print "$pos $song{$pos}{VISITOR_POS} $song{$pos}{TITLE}\n"; }
    If you wanted to sort by the Visitor's position, play a few games with the sort
    for $pos ( sort { $song{$a}{VISITOR_POS} <=> $song{$b}{VISISTOR_POS} } + keys %song ) { print "$pos $song{$pos}{VISITOR_POS} $song{$pos}{TITLE}\n"; }
    and so on.

    Mik
    mikfire ( perlus bigotus maximus )

Re: Fixed 'Top 10' compared with visitors' Top 10
by Shendal (Hermit) on May 26, 2000 at 23:39 UTC
    Here's some quick test code I wrote up:
    %songs = ( 'Insomina' => { 'sales' => '9999', 'votes' => '1' }, 'Enter Sandman' => { 'sales' => '9998', 'votes' => '10' }, 'Bad Moon Rising' => { 'sales' => '9997', 'votes' => '9' } ); sub bysales { $songs{$b}{sales} <=> $songs{$a}{sales}; } sub byvotes { $songs{$b}{votes} <=> $songs{$a}{votes}; } # Print the best songs by sales foreach $ditty ( sort bysales keys songs ) { print "$ditty\n"; } # Print the best songs by votes foreach $ditty ( sort byvotes keys songs ) { print "$ditty\n";
    Of course, TMTOWTDI, as usual.
    HTH!
Re: Fixed 'Top 10' compared with visitors' Top 10
by Anonymous Monk on May 26, 2000 at 23:37 UTC
    Thank you!