Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

perl 'require' in begin block

I have the following code:

#!/usr/bin/env perl
use strict;
use warnings;
use feature 'say';

BEGIN {
       my $supported = undef;
       *compute_factorial = sub { if (eval { require bignum; bignum->import(); 1;}) {
                                    my $num       = shift;
                                    my $factorial = 1;
                                    foreach my $num (1..$num) {
                                        $factorial *= $num; 
                                    }
                                    return $factorial;
                                  }  else {
                                       undef;
                                     } };
       };

my $f = compute_factorial(25);
say $f;

I'm just testing something, not really a production code... I do have bignum pragma on my machine (perfectly loadable using use), I was wondering why require doesn't work as it should be (I'm getting exponential numbers rather then "big numbers") in this case?

Thanks,

like image 725
snoofkin Avatar asked Jul 25 '12 17:07

snoofkin


1 Answers

bignum's import needs to be called before compilation of the code it is intended to effect, or it doesn't work. Here, the BEGIN makes it called before your actual compute_factorial call, but not before the critical my $factorial = 1; is compiled.

A better approach for cases like this is just to directly use Math::Big*:

if (eval { require Math::BigInt }) {
    my $num = shift;
    my $factorial = Math::BigInt->new(1);
    foreach my $num (1..$num) {
        $factorial *= $num;                            
    }
    return $factorial;
} else {
    undef;
} 
like image 103
ysth Avatar answered Sep 23 '22 02:09

ysth