2012-02-15 70 views
2

IM Perl模塊,試圖將模塊File-Copy-Recursive添加到我的劇本,我和另一個模塊已經完成,但是當我嘗試使用它,我得到一個錯誤,我無法解釋:添加相對於腳本

use lib "./cpan"; 
use Recursive qw(dircopy); 
dircopy($path1, $path2); 

我得到的錯誤是:未定義的子程序&主:: dircopy被稱爲...

我不明白它,該模塊顯然有它的功能dircopy。

+1

你嘗試使用完整的軟件包名稱'使用File :: Copy :: Recursive' – run 2012-02-15 10:55:05

+0

該模塊不在我已安裝的標準庫中,我不想依賴那個。我從cpan下載了模塊並將其放置在腳本所在的/ cpan文件夾中。 – 2012-02-15 10:57:58

+0

好的,所以我通過使用 File :: Copy :: Recursive :: dircopy($ path1,$ path2); 在我的代碼。 我不知道爲什麼它只有這種方式,但。 也許有人可以對此發表評論。 – 2012-02-15 11:02:13

回答

4

正如其他答案已經指出,這是行不通的,因爲您已將模塊的位置從File/Copy/Recursive.pm的包含目錄中移動到Recursive.pm

這裏的爲什麼不起作用:

一個Perl 模塊(用.pm擴展名的文件)和一個Perl (特定的代碼命名空間下集)是兩個完全不同的事情。通常情況下,我們會將一個軟件包放入一個碰巧具有相同名稱的模塊中,但這實際上只是爲了幫助我們人類保持我們的理智。 perl不關心的一種方式或其他 - 一個模塊可以包含多個包,一個包可以跨多個文件分割,而包的名稱和模塊可以爲所有關心perl完全無關。

但是,仍然有兩種使用相同名稱的約定,use命令利用這種約定使事情變得更方便一些。在幕後,use Module;意味着require Module.pm; Module->import; - 請注意,它調用導入的模塊名稱,而不是模塊中包含的軟件包的名稱!

而這關鍵是你的問題。即使你已經移動的文件了File/Copy/目錄,其內容仍指定package File::Copy::Recursive,因此,這就是它的所有代碼的結束。 use Recursive試圖呼叫​​3210,這不存在,所以沒有任何東西被導入。 dircopy函數將被導入File::Copy::Recursive->import,但永遠不會被調用。

所以,是的。移動./cpan/Recursive.pm./cpan/File/Copy/Recursive.pm,這樣的包名和模塊名稱將再次匹配和理智將被恢復。 (如果你一直在關注,你應該至少有兩到三種方法來實現這個功能,但是如果你需要保留這個文件,那麼把這個文件移動到./cpan下的適當位置真的是最好的選擇File::Copy::Recursive源代碼位於項目代碼的子目錄中。)

2

使用FindBin相對庫路徑:

use FindBin; 
use lib "$FindBin::Bin/./cpan"; 
use File::Copy::Recursive; 

而且你必須保持整個「樹」下./cpan和使用線必須保持不變。

文件下./cpan DIR:

find ./cpan/ 
./cpan/File/Copy/Recursive.pm 
+0

嗯,我沒有看到差異,因爲我說它已經與另一個模塊一起工作。我犯了同樣的錯誤。 – 2012-02-15 10:41:45

1

在Perl模塊名稱不僅來自路徑,而且從它的package聲明。您所安裝的模塊./cpan,但指定的軟件包名稱仍然是File::Copy::Recursive