Beefy Boxes and Bandwidth Generously Provided by pair Networks
Syntactic Confectionery Delight

USE, but fail nicely

by vaevictus (Pilgrim)
on Feb 01, 2001 at 04:17 UTC ( #55611=perlquestion: print w/replies, xml ) Need Help??

vaevictus has asked for the wisdom of the Perl Monks concerning the following question:

I've got a module i want to load, if available, but if it's not available, I want absolutely nothing to happen. I was told to use eval:
#!/usr/bin/perl -w use strict; eval { use Time::HiRes qw(time); }; print "\n";
fails with
Use of uninitialized value in eval "string" at ./ line 3.
How am I *supposed* to do this?

Replies are listed 'Best First'.
Re: USE, but fail nicely
by tadman (Prior) on Feb 01, 2001 at 04:22 UTC
    #!/usr/bin/perl -w use strict; eval qq{ use Time::HiRes qw(time); }; print "\n";
    Two characters, my friend. eval with braces forces compilation before "evaluation", which makes it function more like do{}. If you pass a scalar, it is compiled after the main program and any compilation errors are directed to the program, not your STDERR. This is the difference between 'eval EXPR' and 'eval BLOCK'.

    The Camel has a lot to say about the Joy of Eval, and so does 'perldoc -f eval'.

    Note that this will "do absolutely nothing" as you requested. Errors from compilation show up in $@ and you can warn, or act accordingly.
Re: USE, but fail nicely
by btrott (Parson) on Feb 01, 2001 at 04:23 UTC
    You do want eval, but not quite like that; unless you put the use into a string, it'll still get run at compile-time and will die anyway. You want:
    eval "use Time::HiRes qw(time)"; die "Nice message: $@" if $@;
Re: USE, but fail nicely
by extremely (Priest) on Feb 01, 2001 at 04:33 UTC
    try: eval 'use Time::HiRes qw(time)';

    The eval {}; form actually tokenizes what is inside the brackets and thus the parser will catch use, no, BEGIN {}, and END{} pragmas and blocks. The string form is just a string till the eval actually happens at runtime.

    Try these at the commandline to see the various behaviors:

    perl -e 'if(shift){eval{BEGIN{print"eek\n"}print"ahh\n"}}' 0 perl -e 'if(shift){eval{BEGIN{print"eek\n"}print"ahh\n"}}' 1 perl -e 'if(shift){eval"BEGIN{print\"eek\n\"}print\"ahh\n\""}' 0 perl -e 'if(shift){eval"BEGIN{print\"eek\n\"}print\"ahh\n\""}' 1

    $you = new YOU;
    honk() if $you->love(perl)

Re: USE, but fail nicely
by Fastolfe (Vicar) on Feb 01, 2001 at 05:38 UTC
    I might attempt this like this, which is a little more verbose than the string version of eval, but "feels" more correct to me (though there's nothing wrong with using that other form of eval):
    BEGIN { eval { require Time::HiRes; import Time::HiRes 'time'; } warn "Couldn't load Time::HiRes, but that's OK\n\t$@" if $@; }
(crazyinsomniac) Re: USE, but fail nicely
by crazyinsomniac (Prior) on Feb 01, 2001 at 04:22 UTC
    After realizing what i did wrong, i changed it to what it was meant to do.
    #!perl -w use strict; eval("use Time::HiRes qw(time);"); if($!){die "blah:$!";}

    "cRaZy is co01, but sometimes cRaZy is cRaZy".
                                                          - crazyinsomniac

Re: USE, but fail nicely
by Trinary (Pilgrim) on Feb 01, 2001 at 04:23 UTC
    use (IIRC) pretends to be a BEGIN block...use eval "require Mod::Ule; import Mod::Ule";

    Um...typos nonwithstanding.


Log In?

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://55611]
Approved by root
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others pondering the Monastery: (3)
As of 2022-01-20 12:13 GMT
Find Nodes?
    Voting Booth?
    In 2022, my preferred method to securely store passwords is:

    Results (56 votes). Check out past polls.