http://qs321.pair.com?node_id=11114842


in reply to declaring lexical variables in shortest scope: performance?

As usually, when you are interested in performance, benchmark or profile.
#! /usr/bin/perl use warnings; use strict; use Benchmark qw{ cmpthese }; sub outer { my $s = 0; my $x; for $x (1 .. 5) { $s += $x; } $s } sub inner { my $s = 0; for my $x (1 .. 5) { $s += $x; } $s } outer() == inner() or die 'Error in implementation'; cmpthese(-2, { outer => 'outer()', inner => 'inner()', });

The result on my machine shows inner is about 6% faster. Such a small difference is insignificant and usually has no real impact on real performance.

Why is that? Remember that for localises its variable when it's not lexical, i.e. it has to store its previous value before entering the loop and restore it at the loop's end. It seems to take a bit more time than just creating a fresh new lexical variable.

map{substr$_->[0],$_->[1]||0,1}[\*||{},3],[[]],[ref qr-1,-,-1],[{}],[sub{}^*ARGV,3]

Replies are listed 'Best First'.
Re^2: declaring lexical variables in shortest scope: performance?
by Anonymous Monk on Mar 31, 2020 at 11:50 UTC
    Benchmark pitfall, overhead drowns out what you're measuring, in line sub contents as strings not sub calls

      I didn't know that! Is the logic behind replacing the sub with a string expression, to fool the cache?

      use Benchmark 'cmpthese'; cmpthese(-2, { predecl => ' my $y; my $x; for $x (1..10000) { $y+=$x } ', lexical => ' my $y; for my $x (1..10000) { $y+=$x } ', }); __END__
      Rate lexical predecl lexical 3996/s -- -0% predecl 4001/s 0% --

      vs

      use Benchmark 'cmpthese'; cmpthese(-2, { predecl => sub { my $y; my $x; for $x (1..10000) { $y+=$x } }, lexical => sub { my $y; for my $x (1..10000) { $y+=$x } }, });
      Rate predecl lexical predecl 4011/s -- -0% lexical 4015/s 0% --

      Which is more or less what haukex and choroba demonstrated.