ich wollte mal checken, was ein eval an Laufzeit kostet, vs precompiled oder ohne eval.
Vielleicht ist mein Beispiel zu trivial oder ganz falsch - deshalb hier zur Diskussion:
#!/usr/bin/perl
# testing speed of eval
use strict;
use warnings;
use Time::HiRes qw(gettimeofday time);
my $j = 0;
my $ts;
# precompile and check for error
my $cval = eval(q{sub {my $foo = shift;return $foo++;} }); ## no critic 'ProhibitStringyEval'
if(!$cval || $@) {
print "evals error $@ \n";
exit;
}
# without eval
sub addone {
my $foo = shift;
return $foo++;
}
# run eval precompiled
$ts = time;
for my $i (0..100000) {
$j = $cval->($i);
}
my $dur = time - $ts;
print " Peval_res= $j dur= $dur \n";
# run evals
$ts = time;
for my $i (0..100000) {
$j = eval ( $i); ## no critic 'ProhibitStringyEval'
}
my $dur1 = time - $ts;
print " eval_res= $j dur= $dur1 \n";
print "Gain= " . $dur1/$dur . " \n";
# run w.o. eval
$ts = time;
for my $i (0..100000) {
$j = addone($i);
}
my $dur2 = time - $ts;
print "NOeval_res= $j dur= $dur2 \n";
# run w.o. sub & eval
$ts = time;
for my $i (0..100000) {
$j = $i++;
}
my $dur3 = time - $ts;
print " NOsub_res= $j dur= $dur3 \n";
exit;
Output:
./evaltest.pl
Peval_res= 100000 dur= 0.59893798828125
eval_res= 100000 dur= 9.32247710227966
Gain= 15.5650122127535
NOeval_res= 100000 dur= 0.576098918914795
NOsub_res= 100000 dur= 0.150755167007446
soll heissen :
- Ein precompiled eval ist um den Faktor 15 schneller als ein inline eval!
- Ein sub Aufruf OHNE eval ist nicht viel schneller als das precompiled eval
- der inline code (ohne sub) ist nochmal um den Faktor 4 scheller - das zeigt in wesentlichen den overhead des sub-calls...
Fragen dazu:
ist das setup valid?
geht es etwas eleganter ? / kürzerer code ?
Die Anforderung ist, dass man zur Laufzeit variaben übergeben kann/muss.
?
l.g. erwin
Ich glaube die Zahlen sind korrekt.
Oder auch: das Eval Overhead enstpricht ca 15 shift+inkrement Operationen, in absoluten Zahlen 0.1ms.
Du musst aber einen langsamen Rechner haben. Mein alter raspi 2 ist 8 mal schneller :)
Wenn wir schon bei effizienter Programmierung sind:
for (my $i=0;$i<=100000;$i++)
ist ca. doppelt so schnell, wie
for my $i (0..100000)
Hi Damian,
re. 8mal schneller: Interessant... Bei mir auch ein alter PI-2 Mdl.B. - allerdings mit Jessie - Perl Version 5.20 - möglicherweise daher die Unterschiede...
Den verwende ich als Test/Development environment, falls dort funktioniert, teste ich mit buster u. bullseye...- erst dann gehts ins SVN.
re. for loops: erstaunlich! - wusste ich auch noch nicht....
Ich hatte mich in meiner perl "lern-Kurve" oft am Stil von Rudi orientiert...
PBP meint allerdings, man sollte "C-Style" for loops vermeiden, die Begründung ist m.M. etwas "dünn" (readability/mainainability...), der Author gibt allerdings zu, dass "C-style" for loops üblicherweise schneller sind....