eval 表達式: eval 塊: eval 在第一種形式,一般稱爲一個字符串eval EXPR 返回值是被解析的和被執行的做爲一個小小的Perl程序。 表達式的值(是它自己決定的在標量上下文環境)是有限被解析, 若是這裏沒有錯誤,做爲一個block執行在當前Perl程序的詞法上下文。 這意味着,特別狀況下, 任何外部的詞法變量時可見的,任何包變量設置或者子函數和 格式定義 以後仍舊存在 注意 eval執行值是每次都被解析的, 若是EXPR 被省略, 評估$_. 這種形式是典型的用於延遲解析。 若是unicode_eval 功能是被啓用( 默認是在5.16或者更多的版本) EXPR 或者$_ 是做爲一個字符串,所以 use utf8 聲明沒有影響, 源過濾器是被禁止的。 在沒有unicode_eval的功能下, 字符串有時候回對待爲 字符和做爲字節, 取決於內部編碼,源過濾器激活eval 展示不穩定, 若是字符串擴展一個標量包含一個浮點數. 標量可能擴展爲字母,好比 "NaN" or "Infinity" 在一個use locale的範圍內. 第2中形式中, BLOCK裏的代碼只被解析一次,在同一時間圍繞代碼 eval自己是被解析-- 被執行在當前的Perl程序的上下文。 這種形式一般用來捕獲異常。 最後的分號,若是有的話,能夠從EXPR的值或者BLOCK裏省略 在這兩種形式中, 返回值是最後一個表達式計算的值, 一個return語句也可使用,就像在子函數裏。 表達式提供的返回值是計算爲空白的,標量,或列表上下文, 依賴eval 自己的列表上下文。 若是有一個語法錯誤或者運行時錯誤,或者一個"die" 語句被執行, "eval" 返回undef 在標量上下文環境或者一個空的列表在列表環境, $@是存放錯誤信息的。(在5.16以前,一個bug 致使"undef" 被返回在列表上下文對於符號錯誤, 可是不是運行錯誤) . 若是沒有錯誤, $@是空的字符串。 一個控制流操做像 "last" 或者"goto" 能夠繞過$@設置。 要注意的是,使用"eval" 不會沉默perl輸出警告道STDERR, 也不會把警告信息塞到$@. 須要注意的是,由於"eval" 捕獲其餘致命的錯誤, 它是有用的對於肯定某個特性(好比 做爲socket或者symlink) 是被實現。 若是你想要捕獲錯誤 當加載一個XS模塊, 一些2進制接口的問題(好比Perl 版本傾斜) 多是致命的 甚至是"eval" 除非$ENV{PERL_DL_NONLAZY} 被設置 若是要執行的代碼並無不一樣, 你可能使用eval-BLOCK 從一個捕獲運行錯誤的而不招致 每次從新編譯的處罰 錯誤,若是有的話,仍舊返回在$@ # make divide-by-zero nonfatal 使被零除 eval { $answer = $a / $b; }; warn $@ if $@; # same thing, but less efficient eval '$answer = $a / $b'; warn $@ if $@; # a compile-time error eval { $answer = }; # WRONG # a run-time error eval '$answer ='; # sets $@ [root@wx03 test]# cat a1.pl eval { $answer = $a / $b; }; warn $@ if $@; [root@wx03 test]# perl a1.pl Illegal division by zero at a1.pl line 1. 使用 "eval{}"的形式做爲一個異常捕獲器在libararies 有一些問題。 因爲當前的說的破碎的狀態(__DIE__) 你可能但願不要觸發 any "__DIE__" hooks #一個私有的理財捕獲 對於除以0 [root@wx03 test]# cat a2.pl eval { local $SIG{'__DIE__'}; $answer = $a / $b; }; warn $@ if $@; [root@wx03 test]# perl a2.pl Illegal division by zero at a2.pl line 1. 這是很是重要的,給定的 "__DIE__" hooks 也被稱爲die, 這有可能改變它們的錯誤消息 [root@wx03 test]# cat a3.pl # __DIE__ hooks may modify error messages { local $SIG{'__DIE__'} = sub { (my $x = $_[0]) =~ s/foo/bar/g; die $x }; eval { die "foo lives here" }; print $@ if $@; # prints "bar lives here" } [root@wx03 test]# perl a3.pl bar lives here at a3.pl line 5.