On #perl6 this morning, rokoteko was curious about doing Taylor series in Perl 6. This sort of thing fascinates me, so I quickly coded up this:

sub sine-power($x) {
my $sign = 1;
gather for 1, 3 ... * -> $n {
take $sign * $x ** $n / [*] (1 ... $n);
$sign *= -1;
}
}

That works, and is pretty straightforward. However, it’s got one big glitch in it, IMO. Even if you feed it a Rat input, it will always return a list of Nums, because `$x ** $n`

returns a Num. (Hmmm…. might that be worth changing?)

No problem, you just need to complicate the function a bit by keeping running products for the numerator and denominator:

sub sine-power($x) {
my $sign = 1;
my $x-part = $x;
my $denom = 1;
gather for 3, 5 ... * -> $n {
take $sign * $x-part / $denom;
$sign *= -1;
$x-part *= $x * $x;
$denom *= $n * ($n - 1);
}
}

As a bonus, the new version should be faster.

Let’s see if it works:

> say sine-power(0.1).munch(4).perl;
(1/10, -1/6000, 1/12000000, -1.98412698412698e-11)
> say ([+] sine-power(0.1).munch(3)).perl;
1198001/12000000
> say [+] sine-power(0.1).munch(3);
0.0998334166666667
say sin(0.1);
0.0998334166468282

As you can see, this generates a Rat approximation for sin(0.1) which is accurate to 10 decimal places. Not bad!

### Like this:

Like Loading...

*Related*

This entry was posted on July 20, 2010 at 11:51 am and is filed under Uncategorized. You can follow any responses to this entry through the RSS 2.0 feed.
You can leave a response, or trackback from your own site.

## Leave a Reply