in reply to Slow constants

Update:Wrong! Please ignore content and downvote and see Perl Mouse's info below.

Because Errno exports constant subs into the callers space, whereas the other two use AUTOLOAD to create the subs in their own package space and then &goto them...every time they are used.


Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
Lingua non convalesco, consenesco et abolesco. -- Rule 1 has a caveat! -- Who broke the cabal?
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.

Replies are listed 'Best First'.
Re^2: Slow constants
by Perl Mouse (Chaplain) on Nov 02, 2005 at 15:27 UTC
    whereas the other two use AUTOLOAD to create the subs in their own package space and then &goto them...every time they are used.
    Eh, no. The first time they are used AUTOLOAD creates them and &gotos in them. The second time, the sub is there and the sub is called.

    The difference is that Errno defines all the subs at compile time - they are empty prototyped subs returning a single value - and are hence are being constant folded at compile time. If you use EAGAIN, Perl will substitute the appropriate value at compile time - which avoids all the overhead of calling a subroutine at run time.

    The benchmark is biased towards heavy use of constants. A typical program will only use a few constants, and only a few times in a program. That means that if you'd export a lot of constants the way Errno does, you pay a heavier price at compile time, regardless how often, and how many constants you use. Fcntl however avoids the costs of compiling all the subs you aren't going to use - but the price of using a constant goes up.

    Perl --((8:>*

      Doesn't the absence of an empty prototype in the assignment *$AUTOLOAD = sub { $val } mean that these are just normal (non-constant) subs, and will therefore never be inlined, and therefore, called everytime they are used?

      ## From Socket.pm (Fnctl.pm contains an nearly identical sub) sub AUTOLOAD { my($constname); ($constname = $AUTOLOAD) =~ s/.*:://; croak "&Socket::constant not defined" if $constname eq 'constant'; my ($error, $val) = constant($constname); if ($error) { croak $error; } *$AUTOLOAD = sub { $val }; goto &$AUTOLOAD; }

      Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
      Lingua non convalesco, consenesco et abolesco. -- Rule 1 has a caveat! -- Who broke the cabal?
      "Science is about questioning the status quo. Questioning authority".
      In the absence of evidence, opinion is indistinguishable from prejudice.
        Doesn't the absence of an empty prototype in the assignment *$AUTOLOAD = sub { $val } mean that these are just normal (non-constant) subs, and will therefore never be inlined, and therefore, called everytime they are used?
        Eh, yes. And no. They will indeed by called everytime they are used - just as I said: The second time, the sub is there and the sub is called. (But a subsequent call to the same constant will not invoke AUTOLOAD again). However, it does not matter whether there's a prototype present or not - the calling code is already compiled, so it's too late for inlining. Although it might matter if there's future code to be string-evalled that uses a previous called constant.
        Perl --((8:>*
      Thanks for your answers!
      Now it's time to meditate a little... :)