Beefy Boxes and Bandwidth Generously Provided by pair Networks
Keep It Simple, Stupid

Smart match in p5

by xmath (Hermit)
on Mar 13, 2005 at 12:18 UTC ( #439084=perlmeditation: print w/replies, xml ) Need Help??

In response to Juerd's request for a smart match operator in perl 5, I've implemented a patch which adds it to the parser.   -- See the README for installation instructions.

The actual smart matching is expected to be implemented by a perl module, an outline of which can be found in the above directory.

Note that prefix '~~' still works like it did previously. Therefore if foo is a sub, then foo~~bar will be parsed as foo(~~bar) unless foo has prototype ().

So.. any other syntax that would be nice to hack into perl?   :-)

Update (14:39 CET) -- Revised version, see README for changes.

Update (00:12 CET) -- Added negated smart match (!~~)

Replies are listed 'Best First'.
Re: Smart match in p5
by Juerd (Abbot) on Mar 14, 2005 at 07:52 UTC


    I'll start working on when I have the time, which should be this week.

    Juerd # { site => '', plp_site => '', do_not_use => 'spamtrap' }

(Revisiting) Smart match in p5
by Roy Johnson (Monsignor) on Apr 04, 2005 at 20:03 UTC
    As an alternative to having hacked syntax, I've written up this little package that does the most useful (in my view) smart matches in a case-ish sort of call.
    #!perl =pod =head1 NAME smatch - smart matching switch construct =head1 SYNOPSIS smatch $val => [ 1, sub { print "number 1" } ], [ 'a', sub { print 'string a' } ], [ [1,10], sub { print 'number in range' } ], # strings work, to +o [ @array, 42, sub { print 'number in list' } ], [ qr/\w+/, sub { print 'pattern' } ], [ \%hash, sub { print 'entry in hash' } ], [ \&sub, sub { print 'arg to sub' } ], [ (), sub { print 'default' } ] ;
    Code and comments follow

    Caution: Contents may have been coded under pressure.
Re: Smart match in p5
by demerphq (Chancellor) on Mar 14, 2005 at 09:35 UTC

    Wouldnt it be better if your patch was against blead and not maint and that you submit it to p5p for review?


      Wouldnt it be better if your patch was against blead and not maint and that you submit it to p5p for review?

      Perhaps. However, I'd like to have a more complete implementation (i.e. one with itself) before sending things over to p5p. I want to avoid discussion of practical problems that simply aren't there, and the only way to do that is to prove it can work before suggesting its inclusion. The advance work usually consumes less time than the discussion avoided by it. Also, I don't care much for the final implementation, and see what we're doing now as a proof of concept (that can very well be implemented without much change, if people like it).

      I haven't needed switch/case or given/when myself. But many, many people would prefer it over if/elsif/else structures.

      Juerd # { site => '', plp_site => '', do_not_use => 'spamtrap' }

        Hope you fare better than I did with my say() patch.

        Examine what is said, not who speaks.
        Silence betokens consent.
        Love the truth but pardon error.
        Lingua non convalesco, consenesco et abolesco.

        IMO a crucial issue to get this into play is to find out how many scripts it breaks. You should have a good estimate of that before proposing it.


        Since it does break backwards compatability, I'm willing to bet that p5p will shoot it down. A smart match operator doesn't seem to fill a great demand (and no, "smart match operator" is not the same as "switch", for which there are alternatives - a "smart match operator" is yet another alternative to "switch").

        They will demand showing you it fills a demand. So they'll suggest you first implement it in a module (a source filter probably).

Re: Smart match in p5
by halley (Prior) on Mar 14, 2005 at 13:52 UTC
    I read Juerd's request. I read the summary of smart matching you linked. I'd like to think I'm not dense, but I don't get what this operator is supposed to do, or why it's better than the various operators that exist?

    Maybe it's because I watched The Fifth Element this weekend, but I read the ~~ as that annoying 'bzzzZZz!' noise which the superstar personality did whenever he wanted other people to divine his vague intentions and to get lost.

    I know Perl is supposed to have lots of DWIM, but another programmer should be able to understand WIM too.

    [ e d @ h a l l e y . c c ]

      I don't get what this operator is supposed to do, or why it's better than the various operators that exist?

      It's one operator to compare anything to anything. It's eq, ==, grep, exists, all in one. That's useful if you want to pass a condition to be applied to a general function. Normally, you'd supply a coderef, but now, you can just supply any value it can be smart matched to. And the great thing is, that you can still pass that coderef.

      The "when" operator implicitly smart-matches against $_.

      given ($address) { when (@whitelist) { $score -= 30 } when (@blacklist) { $score += 50 } when (/example\.com$/) { $score = 0 } default { ... } }
      The smart match operator, in this example invisible because it's used by when internally, avoids a lot of typing. Compare the alternative:
      for my $a ($address) { if (grep $_ eq $a, @whitelist) { $score -= 30; last; } if (grep $_ eq $a, @blacklist) { $score += 50; last; } if ($a =~ /example\.com$/) { $score = 0; last; } ... }
      Smart match replaces grep and =~ here. But it can also replace eq and == and exists, making it a great tool for making code easier to read, especially when implied with given/when.

      Juerd # { site => '', plp_site => '', do_not_use => 'spamtrap' }

      PS The default block { } around ... isn't needed, but it's good documentation.
        I know that idiom plays a large part of understanding a language, but I feel like neither of those examples are particularly self-documenting or literate.

        Saying "Given X, when A, B, C, do T" does not roll off the tongue. It doesn't express any particular relationship between X and the list. It doesn't help me understand what the when operator does. Are we iterating? Triggering? You said "smart matching," but uh, that still leaves my uninitiated brain lost. Also, "when" connotates time or passive reaction to me, not compliance or active processing.

        "Given X, if it matches any of A, B, C, do T" is a step up. Going from a complicated concept of "does whatever you want" to a more specific concept of "performs this particular comparison" is a shift toward self-documentary or literate programming.

        As you can see, I am very dubious of the value of Perl6, and this sort of divergence from pragmatic programming to ethereal ivory-tower philosophizing just doesn't get me any closer to enjoying the changes in the language. The language should express generic problem-solving succinctly, but not so tersely it cannot be understood concretely.

        [ e d @ h a l l e y . c c ]

      Blatent-plug: As brian d foy commented in his review, Perl 6 Now: The Core Ideas Illustrated with Perl 5 has a whole chapter on Switch and smart matching. Sadly it came out before xmath's amazing hack, but there are a few examples in there where smart matching saves a lot of typing and makes code a lot more clear. (Thankfully, there are 22 other chapters - as cool as smart matching is, vector operations and coroutines are much cooler, IMO). So go fork over your cash right a away - I worked harder for your cash than you did ;)


Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlmeditation [id://439084]
Approved by bart
Front-paged by Enlil
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others having an uproarious good time at the Monastery: (4)
As of 2017-03-23 23:25 GMT
Find Nodes?
    Voting Booth?
    Should Pluto Get Its Planethood Back?

    Results (294 votes). Check out past polls.