note
arhuman
You might also try this :<br>
<code>
sub Root2 {
my $num = shift;
my $root = shift;
my $iterations = shift || 10;
if ( $root == 0 ) { return 1 }
if ( $num < 0 ) { return undef }
my $current = Math::BigFloat->new();
my $guess = Math::BigFloat->new( $num / $root );
my $t=Math::BigFloat->new($guess**($root-1)); 1st version : WRONG ! should be in the loop.
for ( 1 .. $iterations ) {
$current = $guess - ( $guess * $t - $num ) / ( $root * $t );
if ( $guess eq $current ) { last }
$t=Math::BigFloat->new($current**($root-1));
$guess = $current;
}
return $current;
}
</code>
<b>The idea behind, is that '**' is MUCH slower than '*', so I exchange 2 '**' for one '**' and 2 '*'</b><br>
It <u>seems</u> indeed to speed things alot :<br>
(I'm sure your numerous tests will make it sure ;-)<br>
<code>
timethese(10,{
'Root'=> sub {Root(1000,60)},
'Root2'=> sub {Root2(1000,60)}});
</code><br>
gives as result :<br>
<br>
Benchmark: timing 10 iterations of Root, Root2...<br>
<b>Root</b>: 104 wallclock secs (104.38 usr + 0.01 sys = 104.39 CPU) @ <b>0.10/s</b> (n=10)<br>
<strike>
<b>Root2</b>: 15 wallclock secs (14.75 usr + 0.00 sys = 14.75 CPU) @ <b>0.68/s</b> (n=10)
</strike><br>
<b>Root2:</b> 97 wallclock secs (92.67 usr + 0.16 sys = 92.83 CPU) @ <b>0.11/s</b> (n=10)<br>
<br>
<B>UPDATE :</B><BR>
Corrected my code! I misplaced the $t calculation outside the loop,<br>
which is wrong beccause $guess change inside the loop.<br>
As you can see it's no more so fast...<br>
<br>"<b>O</b>nly <b>B</b>ad <b>C</b>oders <b>C</b>ode <b>B</b>adly <b>I</b>n <b>P</b>erl" (OBC2BIP)<br>
134419
134419