C's method is to use preprocessing, which I've heard is coming out (in some form) in Perl6. Thus, if DEBUG is set to 0, the compiler would just skip over that code and not even compile it to optimize it away.
As a note, just do
use constant DEBUG => (1);
if you're in 5.6.0 or higher. (It may be available earlier, but I'm not sure.)
------ We are the carpenters and bricklayers of the Information Age. Don't go borrowing trouble. For programmers, this means Worry only about what you need to implement. | [reply] [d/l] |
If you are wondering whether use constant is available in versions prior to 5.6.0, it was introduced in 5.004. In fact if you were using the late 5.003 versions (circa 5.003_90+) it was there in betas leading up to 5.004.
Nevertheless, it's been there for a long time, at least as far as scalars go. Constant hashes and arrays didn't work correctly until around 5.005_03.
--g r i n d e r
| [reply] [d/l] |
You can use a pre-processor with Perl too. See Filter::cpp.
| [reply] |
#!/usr/local/bin/perl
use Benchmark;
use constant DEBUG_C => (1);
sub DEBUG_S() { 1 }
$DEBUG_V = 1;
timethese( 4000000, {
'constant' => sub { my $x = 1 if DEBUG_C; my $y=2; },
'subroutine' => sub { my $x = 1 if DEBUG_S; my $y=2; },
'variable' => sub { my $x = 1 if $DEBUG_V; my $y=2; },
}
);
produces the following (for DEBUG set to 1 and 0)
DEBUG 0, Run 1
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 3 wallclock secs ( 2.00 usr + 0.01 sys = 2.01 CPU) @ 1990049.75/s (n=4000000)
subroutine: 3 wallclock secs ( 1.99 usr + 0.00 sys = 1.99 CPU) @ 2010050.25/s (n=4000000)
variable: 5 wallclock secs ( 3.93 usr + 0.00 sys = 3.93 CPU) @ 1017811.70/s (n=4000000)
DEBUG 0, Run 2
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 1 wallclock secs ( 1.99 usr + 0.00 sys = 1.99 CPU) @ 2010050.25/s (n=4000000)
subroutine: 1 wallclock secs ( 2.13 usr + 0.00 sys = 2.13 CPU) @ 1877934.27/s (n=4000000)
variable: 3 wallclock secs ( 3.85 usr + 0.00 sys = 3.85 CPU) @ 1038961.04/s (n=4000000)
DEBUG 0, Run 3
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 1 wallclock secs ( 2.07 usr + 0.00 sys = 2.07 CPU) @ 1932367.15/s (n=4000000)
subroutine: 1 wallclock secs ( 2.19 usr + 0.00 sys = 2.19 CPU) @ 1826484.02/s (n=4000000)
variable: 3 wallclock secs ( 3.78 usr + 0.00 sys = 3.78 CPU) @ 1058201.06/s (n=4000000)
DEBUG 1, Run 1
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 8 wallclock secs ( 7.47 usr + 0.00 sys = 7.47 CPU) @ 535475.23/s (n=4000000)
subroutine: 8 wallclock secs ( 7.49 usr + 0.00 sys = 7.49 CPU) @ 534045.39/s (n=4000000)
variable: 9 wallclock secs ( 9.13 usr + 0.00 sys = 9.13 CPU) @ 438116.10/s (n=4000000)
DEBUG 1, Run 2
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 8 wallclock secs ( 7.53 usr + 0.00 sys = 7.53 CPU) @ 531208.50/s (n=4000000)
subroutine: 7 wallclock secs ( 7.41 usr + 0.00 sys = 7.41 CPU) @ 539811.07/s (n=4000000)
variable: 8 wallclock secs ( 9.27 usr + 0.00 sys = 9.27 CPU) @ 431499.46/s (n=4000000)
DEBUG 2, Run 3
Benchmark: timing 4000000 iterations of constant, subroutine, variable...
constant: 8 wallclock secs ( 7.38 usr + 0.00 sys = 7.38 CPU) @ 542005.42/s (n=4000000)
subroutine: 8 wallclock secs ( 7.23 usr + 0.00 sys = 7.23 CPU) @ 553250.35/s (n=4000000)
variable: 9 wallclock secs ( 9.06 usr + 0.00 sys = 9.06 CPU) @ 441501.10/s (n=4000000)
Looking at those numbers - sure $DEBUG is a bit slower but I'd say the savings are a wash - especially if there's some network or database code also in the script. The amount of time you save from not using $DEBUG is really down in the noise. The key here is to choose one method and be consistent with it's application across all scripts/modules in your project(s).
-derby | [reply] [d/l] |
I never claimed significant speed improvement.
What I had in mind is debugging thru the perl debugger.
In that case the print statement becomes noise.
I don't want anything to print, I even don't want to
bother to go thru the statement that contains the print.
Oddly, with use constant DEBUG => 0 I indeed step
thru the statement that contains the print: print "whatever\n" if DEBUG.
Worse I also step thru
one line of constant.pm!
With sub DEBUG() { 0 } I still step thru the statement that contains the print.
When debugging one goes from one nextstate opcode to the next. We see that consecutive nextstate statements
are not fusionned as I expected them to be:
Both oneliners give me the same tree:
perl -e ' sub DEBUG() { 0 } ; use O qw( Concise -exec); print "toto" if DEBUG; print "toto" if DEBUG'
perl -e ' use constant DEBUG =>0; use O qw( Concise -exec); print "tot
+o" if DEBUG; print "toto" if DEBUG'
1 <0> enter
2 <;> nextstate(main 1 -e:1) v
3 <;> nextstate(main 1 -e:1) v
4 <@> leave[t1] vKP/REFC
I don't understand how I get thru one line of constant.pm when debugging using constants!!!
I tested using perl 5.6.1
-- stefp | [reply] [d/l] [select] |
sub DEBUG () { 0 }
I still step through the DEBUG subroutine. Which is what
I would expect while debugging. Try:
perl -de 'use constant DEBUG =>0; use O qw( Concise -exec); print "toto" if DEBUG; print "toto" if DEBUG'
perl -de 'sub DEBUG() { 0 }; use O qw( Concise -exec); print "toto" if DEBUG; print "toto" if DEBUG'
-derby | [reply] [d/l] |
| [reply] |
The link you posted has changed, the article has been moved here.
| [reply] |
I usually end up using the variable rather than the
constant since it's very easy to alter this using
a command line option (e.g. the ubiquitous '-d'). I hate
to edit code to get additional diagnostics printed
out for a program that is giving me problems (esp. on a
production machine). If the program is large and I have
a good logging mechanizm built in, then a constant is
usually fine though.
Just curious, does anyone know if there is an easy, clean way of
doing this with 'use constant'?
bluto
| [reply] |
sub say {
print "$_[0]\n";
}
sub moan {
print STDERR "WARNING: $_[0]\n";
}
sub mutter {
print "debug: $_[0]\n";
}
if (!$DEBUG) {
eval "sub mutter { }";
}
Then the code reads well too :-) | [reply] [d/l] |