Combinations and permutations: Difference between revisions

Line 209:
 
=={{header|Perl 6}}==
Perl 6 is fairly limited with very large floating values. It tends to consider them as infinite when they reach <math>10^{300}</math> or so. This forces us to use only logarithms and to tweak them in order to show the exponential.
{{incomplete}}
===Exact values===
<lang perl6>sub P($n, $k) { [*] $n - $k + 1 .. $n }
sub C($n, $k) { P($n, $k) / [*] 1 .. $k }
 
<lang perl6>submulti P($n, $k) { [*] $n - $k + 1 .. $n }
for (1..12).roll(3) -> $n {
multi myC($n, $pk) ={ P(^$n, $k) / [*] 1 .pick;. $k }
say "P($n, $p) = {P($n, $p)}";
sub lgamma(\z) {
z < 10 ?? lgamma(z+1) - log(z) !!
.5*log(2*pi*z) +
z*log(z/e+1/(12*e*z)) -
log(z)
}
 
multi P($n, $k, :$float!) {
for (10..60).roll(3) -> $n {
my $plog = lgamma(^$n+1) - lgamma($n -$k +1).pick;
my $e = ($log/10.log).Int;
sprintf "%.8fE%+d", exp($log - $e*10.log), $e;
}
multi C($n, $k, :$float!) {
my $log = lgamma($n+1) - lgamma($n -$k +1) - lgamma($k+1);
my $e = ($log/10.log).Int;
sprintf "%.8fE%+d", exp($log - $e*10.log), $e;
}
 
say "Exact results:";
for (1..12).roll(3) -> $n {
my $p = $n div 3;
say "P($n, $p) = {P($n, $p)}";
}
for (10, 20 ..60).roll(3) 60 -> $n {
my $p = $n div 3;
say "C($n, $p) = {C($n, $p)}";
}
 
say;
say "Floating point approximations:";
for 5, 50, 500, 1000, 5000, 15000 -> $n {
my $p = $n div 3;
say "P($n, $p) = {P($n, $p, :float)}";
}
 
for 100, 200 ... 1000 -> $n {
my $p = $n div 3;
say "C($n, $p) = {C($n, $p, :float)}";
}</lang>
{{out}}
<pre>P(3,Exact 1) = 3results:
P(91, 0) = 1
P(2, 0) = 1
P(3, 1) = 3
P(4, 1) = 4
CP(455, 241) = 37736557501505
CP(166, 12) = 1630
CP(487, 302) = 7309837001104</pre>42
P(8, 2) = 56
P(9, 3) = 504
P(10, 3) = 720
P(11, 3) = 990
P(12, 4) = 11880
C(10, 3) = 120
C(20, 6) = 38760
C(30, 10) = 30045015
C(40, 13) = 12033222880
C(50, 16) = 4923689695575
C(60, 20) = 4191844505805495
 
Floating point approximations:
P(5, 1) = 5.00000000E+0
P(50, 16) = 1.03017326E+26
P(500, 166) = 3.53487492E+434
P(1000, 333) = 5.96932629E+971
P(5000, 1666) = 6.85674576E+6025
P(15000, 5000) = 9.64985399E+20469
C(100, 33) = 2.94692433E+26
C(200, 66) = 7.26975256E+53
C(300, 100) = 4.15825147E+81
C(400, 133) = 1.25794868E+109
C(500, 166) = 3.92602839E+136
C(600, 200) = 2.50601778E+164
C(700, 233) = 8.10320356E+191
C(800, 266) = 2.64562336E+219
C(900, 300) = 1.74335637E+247
C(1000, 333) = 5.77613455E+274</pre>
 
=={{header|Racket}}==
1,934

edits