2013-06-29 34 views
8

documentation for the open function顯示open()作爲語法:爲什麼Perl open()文檔使用兩種不同的FILEHANDLE樣式?

  • 開放FILEHANDLE,EXPR
  • 開放FILEHANDLE,MODE,EXPR
  • 開放FILEHANDLE,MODE,EXPR,LIST
  • 開放FILEHANDLE,MODE,REFERENCE
  • 開放FILEHANDLE

下的例子,他們有地方其中一個正常的$ -prefixed變量用於文件句柄:

open(my $fh, "<", "input.txt") 

,並例子,其中使用裸詞:

open(FOO, "|tr '[a-z]' '[A-Z]'"); 

一個問題是什麼是每個樣式的名稱,如「我在每種情況下都使用_ _作爲文件句柄?另一種是,爲什麼他們開始在文檔中使用裸詞作爲open()?它似乎是後來的用途都不涉及正常的文件名open() s。在這些情況下,$ -prefixed表單是不可接受的嗎?

+1

很好的問題,我一直都被這個語法困擾 – qwwqwwq

+0

有點討厭以任何其他方式打開(STDOUT,「| less」)'。 – tchrist

回答

20

裸詞形式本質上只是向後兼容的歷史傳統。使用詞法變量幾乎總是新代碼中的正確事情。

→順帶$x詞法標量,其中FOO是,如你所說,稱爲裸詞

詳情/題外話

只是爲了保持完整性,如@Joe_Z中指出,註釋,詞法文件句柄對象是「相對較新的」,作爲Perl 5.005和5.6之間相當主要的重寫的一部分(它們甚至在該版本號中獲得了整個數量級的...)。

然而,在技術上,裸字FOO(或例如STDIN)在單獨的命名空間中被解釋爲僅用於文件句柄。由於沒有一個印記(如$ @ % &)的文件句柄的命名空間,只有兩種方式在該命名空間來引用文件句柄:

  • 你可以參考它的某些功能的間接對象插槽,如print,誰會(幕後)推斷,由於歷史原因,一個裸詞必須指一個文件句柄;
  • 您可以使用類型球,如*FOO,它指的是「任何名稱空間中碰巧與符號FOO綁定的任何內容。

注意,在一些語言如C或方案,一個符號沒有類型印記,所以所有符號只能以一種方式來約束(例如,一個不能有一個變量命名printf和功能命名printf在C ...一般),而在Perl或(例如)Common Lisp,相同的符號foo可以綁定許多不同的東西;區別在於Perl在大多數情況下實際上要求您使用標識來消除「您的意思是哪個foo」。 $foo@foo = @foo[ $x .. $y],$foo[ $n ],%foo = @foo{ $k1, $k2 } = $foo{ $k },&foo等等。

通過使用裸字作爲文件句柄,雖然你失去了一些能力:

值得注意的是,以局部或詞彙(而非全球),你需要綁定符號在每一個命名空間,因爲它們綁定沒有可用的印記。因此,my $foomy @foo可以生活在兩個不同的scratchpad(示波器)中,其中一個可能超過另一個;但my *foo將包括這些,以及文件句柄foo(和潛在的其他不明顯的角落案例,如format說明符,但我不會發誓)。

將裸詞式文件句柄傳遞給函數等等也非常困難。

基本上,裸詞繼承了全局範圍的所有缺點,並且沒有詞法變量的優點。

perldoc perldata上有一個很好的部分Typeglobs和Filehandles這可能更清楚地解釋這些事情。我沒有我的副本,但我相信駱駝對這個主題也有更多的細節。

+5

+1:使用詞法文件句柄是'做它的方法',即使它是Perl,所以TMTOWTDI(有多種方法可以做到這一點)。 –

+1

@JonathanLeffler既是一個強項也是一個缺陷。 – jordanm

+0

因爲我有點舊skool我偶爾在答案中使用glob風格的文件句柄,並總是得到負面評論關於此:)同意,詞法文件句柄更好,但這是一個很難打破的習慣! – Vorsprung

2

正如BPRocock說,my $x是首選,這些天,而FOO被認爲是過時,因爲FOO是一種全局變量,因此它可能會在另一個地方使用的名稱衝突。還有一個原因是$x被鼓勵:$x將在範圍的末尾自動編輯close

相關問題