So what does it buy you over if-else? Not a lot, in my experience. You can save some keystrokes by not retyping what you're matching against, and sometimes the ability to control whether things "fall through" -- matching multiple cases -- can come in handy.
Of course, we are not entirely without alternatives in Perl5. For simple multi-candidate equality testing without defaulting or fall-through, you can use a hash:
Grep is a natural tool for multi-way matching, and you can set it up to do fall-through and defaulting, though you do have to work at it:my $consider = 'foo'; ${{ bar => sub { print "Barred!\n" }, foo => sub { print "Fooed for thought...\n" } }}{$consider}();
Clearly you could encapsulate this in a function that takes your given and the list of condition-then(-break) sub pairs/triplets.{ my $continue = 1; $_->[1]() for grep { my ($cond, $then, $break)=@$_; local $_='boz'; # This is your given $continue and $cond->() and do { $continue = !defined $break; 1} } [sub {/z/}, sub { print "Hi!\n" }], [sub {/o/}, sub { print "Oh!\n" }, 'break'], [sub {1}, sub { print "This is the default\n" }] ; }
Still not pretty enough? Then maybe I can interest you in something that looks a lot like Perl6's given (even though I think it should have been called "consider" for better reading):
Given can only consider a scalar, but otherwise it's pretty comparable to the Perl6 critter, eh?{ my $continue = 1; sub given ($$) { local $_ = shift; my $next = shift; my ($cond, $then); while ($next) { ($cond, $then, $next) = @$next; $then->() if $cond->() and $then; $continue or last; } } sub when (&$) { [$_[0], @{$_[1]}] } sub then (&;$) { [@_] } sub default(&) { [@_] } sub done() { $continue = 0 } sub isit ($$) { my @args=@_; [sub { $_ eq $args[0] }, @{$args[1]}] +} } given 'baz', isit 'baz', then { print "String match!\n" } when {/z/} then { print "Hi!\n" } when {/o/} then { print "Oh!\n"; done } default { print "This is the default\n" } ;
Update: added isit sub, to provide implicit eq check against $_. Writing when {$_ eq 'something'} for a lot of cases would get pretty old.
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re: Switch/case (given/when) in Perl5
by Roy Johnson (Monsignor) on Mar 23, 2005 at 15:21 UTC | |
|
Re: Switch/case (given/when) in Perl5
by Anonymous Monk on Mar 23, 2005 at 17:16 UTC | |
by TimToady (Parson) on Mar 24, 2005 at 05:30 UTC | |
by Anonymous Monk on Mar 24, 2005 at 09:48 UTC | |
by TimToady (Parson) on Mar 24, 2005 at 16:43 UTC | |
|
Re: Switch/case (given/when) in Perl5
by CountZero (Bishop) on Mar 23, 2005 at 21:54 UTC | |
by doom (Deacon) on Mar 24, 2005 at 03:46 UTC |