http://www.perlmonks.org?node_id=495627

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

hello there.
i need some help here. what im trying to do is to list out combinations of a given array of strings, numbers, etc.

for example:
if i had an array like qw(a b c), i would like to generate combinations of the array above, so that i would have:
qw(a b c), qw(a c b), qw(b a c), qw(b c a), qw(c a b), and qw(c b a)

is there a way, in Perl, to come up with the result above? please help. thanx.

ps: to find out how many different combinations can be produced from an array of n elements, use factorial (!). for example, if i had an array of 5 elements, my combinations will have a total of
5! = 5x4x3x2x1 = 120 different combinations

Replies are listed 'Best First'.
Re: generate combinations of lists
by ikegami (Patriarch) on Sep 28, 2005 at 06:07 UTC

    Those are permutations, not combinations. Order doesn't matter for combinations.

    Algorithm::Loops has a function called NextPermute which iterates permutations. Taken almost verbatim from the documentation:

    use Algorithm::Loops qw( NextPermute ); my @list = sort qw( a b c ); do { print(join(', ', @list), "\n"); } while (NextPermute(@list));
Re: generate combinations of lists
by gargle (Chaplain) on Sep 28, 2005 at 07:27 UTC

    Hi,

    update: clarification

    disclaimer: bogoperm, but it does fit your description of the problem!

    #!/usr/bin/perl use strict; use warnings; ############# # bogoperm! # ############# my @array = qw(a b c); my $length = @array; # faculty my $fac = 1; foreach my $f (1..$length) { $fac *= $f; } # my results my %hash = (); # internals my $check; # if equals control then we found a number my $control; # has to contain something like 123... my $index; # the number itself, it's an index! my $count = 0; # 'till this equals $fac OUTER: do { INNER: while (1) { do { $check = 0; $control = 0; $index = 0; foreach my $i (1..$length) { my $number = 1+int(rand()*$length); $index += $number * 10**($i-1); $check += 10**$number; $control += 10**$i; } $check /= 10; $control /= 10; } while ($check != $control); last INNER if defined $hash{$index}; $hash{$index}++; $count++; } } while $count != $fac; # print out the results foreach my $i (keys %hash) { my $j; do { $j = $i % 10; print $array[$j-1]; $i = ($i - $j) / 10; } while ($i > 0); print "\n"; }

    output:

    bash-3.00$ ./perm.pl cba acb bac cab abc bca

    I'll leave it as an exercise to put the output in real lists.

    Well, at least I used strict and warnings :o

    --
    if ( 1 ) { $postman->ring() for (1..2); }
    A reply falls below the community's threshold of quality. You may see it by logging in.
Re: generate combinations of lists
by planetscape (Chancellor) on Sep 28, 2005 at 05:13 UTC

    Please see this. Show us what you have already tried in order to solve the problem yourself.

    HTH,

    planetscape
Re: generate combinations of lists
by kprasanna_79 (Hermit) on Sep 28, 2005 at 07:16 UTC
    Hi gpm,

    Can u please check Link. U may get some better idea to finish your task easier.

    -Prasanna.K
Re: generate combinations of lists
by Skeeve (Parson) on Sep 28, 2005 at 07:19 UTC
    Sounds like homework and I don't think the second answer is the one the teacher wants to see ;-)

    $\=~s;s*.*;q^|D9JYJ^^qq^\//\\\///^;ex;print