Beefy Boxes and Bandwidth Generously Provided by pair Networks
Clear questions and runnable code
get the best and fastest answer
 
PerlMonks  

what difference between eval and do ?

by Anonymous Monk
on Apr 19, 2018 at 03:14 UTC ( [id://1213149]=perlquestion: print w/replies, xml ) Need Help??

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

I thought do BLOCK and eval BLOCK were the same except the last one traps error. But I'm wrong!
my @dd = (1..10); grep { s/\d+/a/ } do {@dd}; print @dd; # aaaaaaaaa +a my @dd = (1..10); grep { s/\d+/a/ } eval{@dd}; print @dd; # 123456789 +10
seems 'eval' make a copy but 'do' not, any comment?

Replies are listed 'Best First'.
Re: what difference between eval and do ?
by ikegami (Patriarch) on Apr 19, 2018 at 03:38 UTC

    First of all, make the intent of your code clear.

    grep { s/\d+/a/ } @dd;
    should be
    @dd = map { s/\d+/a/r } @dd;
    or
    for (@dd) { s/\d+/a/; }
    or
    s/\d+/a/ for @dd;

    Unlike grep and do, eval makes a copy of the values returned like a sub call.

    $ perl -E'@dd = 0..9; s/\d+/a/ for @dd; say @dd;' aaaaaaaaaa $ perl -E'@dd = 0..9; s/\d+/a/ for grep { 1 } @dd; say @dd;' aaaaaaaaaa $ perl -E'@dd = 0..9; s/\d+/a/ for do { @dd }; say @dd;' aaaaaaaaaa $ perl -E'@dd = 0..9; s/\d+/a/ for sub :lvalue { @dd }->(); say @dd;' aaaaaaaaaa $ perl -E'@dd = 0..9; s/\d+/a/ for sub { @dd }->(); say @dd;' 0123456789 $ perl -E'@dd = 0..9; s/\d+/a/ for map { $_ } @dd; say @dd;' 0123456789 $ perl -E'@dd = 0..9; s/\d+/a/ for eval { @dd }; say @dd;' 0123456789
      grep { s/\d+/a/ } @dd;

      This is another instance of a mystery of which I've only recently become aware: The (mis(mis))use of grep in place of the (mis)use of map in place of a for-loop. See this discussion. Just for the satisfaction of my own curiosity, if you or anyone can offer any insight into the rationale behind this strange map/grep usage, I'd be mighty obliged.


      Give a man a fish:  <%-{-{-{-<

        This is another instance of a mystery of which I've only recently become aware: The (mis(mis))use of grep in place of the (mis)use of map in place of a for-loop.
        Definitely agreed that it's a strange (mis|ab)?use of grep, but the map variant seems pretty canonical to me - it transforms the elements of a list and stores the resulting new list. The only thing that strikes me as questionable about it is that it overwrites the original list with the new one.

        This is just a case of "When all you have is a hammer, everything looks like a nail". Drives me nutty too...

      Understood! eval is actually a anonymous sub call, but do is just a block! Thank you very much ikegami!
        eval is also Perl's mechanism for exception-trapping.
Re: what difference between eval and do ?
by Eily (Monsignor) on Apr 19, 2018 at 15:38 UTC

    Another difference:

    sub hello_do { do { return; }; print "Hello from hello_do\n"; } sub hello_eval { eval { return; }; print "Hello from hello_eval\n"; } hello_do(); hello_eval(); __DATA__ Hello from hello_eval
    return is the return value of the eval itself, but the return value of the function calling do.

      As I replied before, That's because eval is a sub call, but do is a block. just image: s/eval/sub Foo/

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://1213149]
Approved by marto
Front-paged by Discipulus
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others admiring the Monastery: (5)
As of 2024-03-28 20:30 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found