[Israel.pm] Indirect method call's in mod_perl

Gaal Yahas gaal at forum2.org
Tue Jun 15 03:48:02 PDT 2004

On Tue, Jun 15, 2004 at 12:26:40PM +0200, Itzik Lerner - Orpak wrote:
> In mod_perl coding style written:
> Avoid indirect method calls, e.g. 
>     Do:
>        CGI::Cookie->new 
>     Don't: 
>         new CGI::Cookie.
> Can someone explain why ?

perlobj, "Indirect Object Syntax":

       For example, a call to a method "new" in indirect notation --
       as C++ programmers are wont to make -- can be miscompiled into
       a subroutine call if there's already a "new" function in scope.
       You#d end up calling the current package's "new" as a subroutine,
       rather than the desired class's method.  The compiler tries to
       cheat by remembering bareword "require"s, but the grief when it
       messes up just isn't worth the years of debugging it will take
       you to track down such subtle bugs.

       There is another problem with this syntax: the indirect object
       is limited to a name, a scalar variable, or a block, because
       it would have to do too much lookahead otherwise, just like any
       other postfix dereference in the language.  (These are the same
       quirky rules as are used for the filehandle slot in functions
       like "print" and "printf".)  This can lead to horribly confusing
       precedence problems, as in these next two lines:

           move $obj->{FIELD};                 # probably wrong!
           move $ary[$i];                      # probably wrong!

       Those actually parse as the very surprising:

           $obj->move->{FIELD};                # Well, lookee here
           $ary->move([$i]);                   # Didn't expect this one, eh?

       Rather than what you might have expected:

           $obj->{FIELD}->move();              # You should be so lucky.
           $ary[$i]->move;                     # Yeah, sure.

       To get the correct behavior with indirect object syntax, you
       would have to use a block around the indirect object:

           move {$obj->{FIELD}};
           move {$ary[$i]};

       Even then, you still have the same potential problem if there
       happens to be a function named "move" in the current package.
       The "->" notation suffers from neither of these disturbing ambi#
       guities, so we recommend you use it exclusively.  However, you
       may still end up having to read code using the indirect object
       notation, so it's important to be familiar with it.

Gaal Yahas <gaal at forum2.org>

More information about the Perl mailing list