Beefy Boxes and Bandwidth Generously Provided by pair Networks
Welcome to the Monastery
 
PerlMonks  

Bug in List::Util::shuffle ?

by matija (Priest)
on Dec 06, 2008 at 14:44 UTC ( #728554=perlquestion: print w/ replies, xml ) Need Help??
matija has asked for the wisdom of the Perl Monks concerning the following question:

I'm working on a project which uses TheSchwartz, and I saw that it was supposed to work with multiple databases.

I was not sure how it would maintain some of it's stuff over more than one database, so I tested it - and found that all the stuff kept going to the same database server.

I looked at the source, and found that it's routine for shuffling databases uses Util::List, and so I tested it:

perl -e 'use List::Util qw(shuffle); @a=[1,2,3,4,5,6,7,8,9,10]; foreac +h (1..24) { print join(",",@ { shuffle(@a) })."\n"}'
That gave me:
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
1,2,3,4,5,6,7,8,9,10
The shuffle routine in List::Util looks reasonable at first glance:
sub shuffle (@) { my @a=\(@_); my $n; my $i=@_; map { $n = rand($i--); (${$a[$n]}, $a[$n] = $a[$i])[0]; } @_; }
Personally, I'm never comfortable using floating point values for array indices, but perhaps there's a perl magic at work that I don't understand. At any rate, either there's a bug in shuffle, or something is very wrong with my random generator - or am I, along with the author of TheSchwartz using List::Util::shuffle incorrectly?

Comment on Bug in List::Util::shuffle ?
Select or Download Code
Re: Bug in List::Util::shuffle ?
by friedo (Prior) on Dec 06, 2008 at 14:50 UTC

    You're shuffling a one-element list containing an array reference, then dereferencing that. A one-element list has only one possible order.

    Try this instead:

    perl -e 'use List::Util qw(shuffle); @a=(1,2,3,4,5,6,7,8,9,10); foreac +h (1..24) { print join(",",shuffle(@a) )."\n"}'

      Aaaggghhh! You're right! I hate it when I do something stupid like that...
Re: Bug in List::Util::shuffle ?
by PetaMem (Priest) on Mar 23, 2009 at 08:58 UTC

    Well - maybe not a bug, but does anyone know the answer to the question in this thread 5 years ago?

    I asked myself the same question today. Unfortunately, the List::Util POD doesn't answer it, neither does the source or (lack of) remarks.

    It certainly doesn't look like the Fisher-Yates described in the Perl Cookbook on p. 121

    Bye
     PetaMem
        All Perl:   MT, NLP, NLU

      The implementation seems to be identical to the modern version of the Fisher-Yates shuffle, as found again by Richard Durstenfeld and published by Donald Knuth.

Log In?
Username:
Password:

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

How do I use this? | Other CB clients
Other Users?
Others rifling through the Monastery: (4)
As of 2015-07-04 21:26 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (60 votes), past polls