[ Perl tips index ]
[ Subscribe to Perl tips ]
In the last Perl tip we briefly mentioned List::MoreUtils. This module
(available from the CPAN) provides a wealth of utility methods for working
with lists and arrays. Most of these methods are trivial to write for
yourself, but have been implemented directly in C so they run as fast as
possible even with large lists.
List::MoreUtils provides a great many list operations, but in this tip
we'll just examine the most common and easy-to-use set operations. Each of
these takes a common form:
operation { condition } @list
For example:
# Check to see if any elements are odd
if ( any { $_ % 2 } @numbers ) {
print "Some of these elements are odd.\n";
}
any returns true if there is at least one element for which the block
returns a true value.
Consider the childhood hangman game. In this game we may wish to compare a single guess against all the letters in the word:
use List::MoreUtils qw(any);
# See if they've correctly guessed a letter
if( any { $letter eq $_ } split //, $word ) {
print "$letter is in my word!\n";
$guesses{$letter}++;
}
all returns true if every element causes the block to return a true
value.
For our hangman game, we could use this to see if they've guessed our entire word:
use List::MoreUtils qw(all);
# See if they've spelled out the whole word yet
if( all { exists $guesses{$_} } split //, $word ) {
print "You have guessed all the letters, well done!\n\n";
last;
}
none returns true if no element causes the block to return a true value,
and part allows us to divide a list into those which cause the block to
return a false value and those which return a true value.
use List::MoreUtils qw(none part);
# Game over.
# See how many letters they guessed correctly
if( none { exists $guesses{$_} } split //, $word) {
print "You didn't guess a single letter correctly!\n";
}
else {
my %word;
@word{ split //, $word} = ();
my ($incorrect, $correct) = part { exists $word{$_} } keys %guesses;
print "You guessed ", scalar(@$correct),
" letters correctly (@$correct)\n";
print "You guessed ", scalar(@$incorrect),
" letters incorrectly (@$incorrect)\n";
}
If we didn't care which letters were guessed correctly and incorrectly, but
instead care just how many letters have been guessed incorrectly we can use
false.
my $wrong_guesses = false { exists $guesses{$_} } split //, $word);
Of course, true does the opposite of false, returning the number of
elements that caused our block to return a true value.
In addition to the operations described above, List::MoreUtils provides
subroutines to allow you to find list indexes or insert elements into parts
of your array. You can iterate over multiple arrays, multiple values, zip
arrays together, find the minimum and maximum values, and more.
Check out List::MoreUtils for more information.
[ Perl tips index ]
[ Subscribe to Perl tips ]
This Perl tip and associated text is copyright Perl Training Australia. You may freely distribute this text so long as it is distributed in full with this Copyright noticed attached.
If you have any questions please don't hesitate to contact us:
| Email: | contact@perltraining.com.au |
| Phone: | 03 9354 6001 (Australia) |
| International: | +61 3 9354 6001 |
Copyright Perl Training Australia. Contact us at contact@perltraining.com.au