2010-08-26 78 views
4

我有一些代碼需要應用程序完全加載和編譯,然後才能執行。如何檢查Perl編譯是否已經完成?

有沒有辦法來檢查我的Perl程序是否仍處於編譯階段?

我有一些作品,但必須有一個更好的辦法:

sub check_compile { 
    printf("checking\n"); 
    foreach my $depth (0..10) { 
    my ($package, $filename, $line, $subroutine) = caller($depth); 
    last unless (defined($package)); 

    printf(" %s %s %s %s %s\n", $depth, $package, $filename, $line, $subroutine); 

    if ($subroutine =~ /::BEGIN$/) { 
     printf("in compile\n"); 
     return 1; 
    } 

    } 

    printf("not in compile\n"); 
    return 0; 
} 


BEGIN { 
    check_compile(); 
} 

use subpkg; 

check_compile(); 

和subpkg.pm包含:

package subpkg; 

use strict; 
use warnings; 

printf("initing subpkg\n"); 
main::check_compile(); 

1; # successfully loaded 
+0

爲什麼不在編譯完成後簡單地設置全局標誌,並檢查該標誌的值? – Ether 2010-08-26 23:32:29

回答

6

我假設你的代碼並沒有太大的利用eval - 否則編譯將與執行「混合」 - 但您可以查看使用INIT和類似塊here作爲簡化此操作的可能方法。

INIT塊被運行 Perl的運行開始之前執行,在 「先入先出」(FIFO)順序。

+0

當然。現在你提到它,這似乎很明顯。看起來像Perl'd有一個狀態變量反映了這一點。 – mmccoo 2010-08-26 23:37:36

+0

'eval'不是將編譯混合到運行時的唯一方法。 'require'和'do'也會在正常執行過程中提取新代碼並進行編譯。 – 2010-08-27 05:32:10

2

$^S in perlvar

解釋的當前狀態。

 
    $^S   State 
    --------- ------------------- 
    undef  Parsing module/eval 
    true (1) Executing an eval 
    false (0) Otherwise 

第一狀態可以在$ SIG {DIE}和$ SIG {發生WARN }處理。

 
    BEGIN { print "Compile $^S\n" } 
    print "Run-time $^S\n"; 
    eval { print "Eval $^S\n" }; 

 
    Compile 
    Run time 0 
    Eval 1 
+0

編譯時'eval's(也就是'BEGIN'塊中的'eval')也沒有定義'$^S' – mob 2010-08-26 23:20:11

+0

我沒有在我的問題中使用過的其他軟件包是' d。初始化代碼在$^S爲真時發生。那時候,還有更多的編譯需要完成。 – mmccoo 2010-08-26 23:27:24

-1

未經檢驗的,但據我所知應該這樣做:

sub main_run_phase_entered { 
    local [email protected]; 
    ! eval q!use warnings FATAL => 'all'; CHECK{} 1! 
} 

更新:不,在END {}塊失敗,我(與5.10.1)。 CHECK {}不運行,但也不會抱怨。