Perl - 檔案 I/O



檔案處理的基礎知識很簡單:你將一個檔案控制代碼與外部實體(通常是檔案)關聯起來,然後使用Perl中的各種運算子和函式來讀取和更新與檔案控制代碼關聯的資料流中儲存的資料。

檔案控制代碼是Perl內部命名的結構,它將物理檔案與名稱關聯起來。所有檔案控制代碼都能夠進行讀/寫訪問,因此您可以讀取和更新與檔案控制代碼關聯的任何檔案或裝置。但是,當您關聯檔案控制代碼時,您可以指定開啟檔案控制代碼的模式。

三個基本檔案控制代碼是 - STDINSTDOUTSTDERR,它們分別代表標準輸入、標準輸出和標準錯誤裝置。

開啟和關閉檔案

Perl中可以使用以下兩個具有多種形式的函式來開啟任何新的或現有的檔案。

open FILEHANDLE, EXPR
open FILEHANDLE

sysopen FILEHANDLE, FILENAME, MODE, PERMS
sysopen FILEHANDLE, FILENAME, MODE

這裡FILEHANDLE是由open函式返回的檔案控制代碼,EXPR是包含檔名和開啟檔案模式的表示式。

Open 函式

以下是以只讀模式開啟file.txt的語法。這裡的小於號<表示檔案必須以只讀模式開啟。

open(DATA, "<file.txt");

這裡DATA是檔案控制代碼,將用於讀取檔案。這是一個示例,它將開啟一個檔案並將內容列印到螢幕上。

#!/usr/bin/perl

open(DATA, "<file.txt") or die "Couldn't open file file.txt, $!";

while(<DATA>) {
   print "$_";
}

以下是以寫入模式開啟file.txt的語法。這裡大於號>表示檔案必須以寫入模式開啟。

open(DATA, ">file.txt") or die "Couldn't open file file.txt, $!";

此示例實際上在開啟檔案進行寫入之前會截斷(清空)檔案,這可能不是預期的效果。如果要開啟檔案進行讀取和寫入,可以在>或<字元前面加上加號。

例如,要開啟檔案進行更新而不截斷它:

open(DATA, "+<file.txt"); or die "Couldn't open file file.txt, $!";

要先截斷檔案:

open DATA, "+>file.txt" or die "Couldn't open file file.txt, $!";

您可以以追加模式開啟檔案。在此模式下,寫入點將設定為檔案的末尾。

open(DATA,">>file.txt") || die "Couldn't open file file.txt, $!";

雙>>以追加模式開啟檔案,將檔案指標放在末尾,以便您可以立即開始追加資訊。但是,除非您還在其前面加上加號,否則無法從中讀取:

open(DATA,"+>>file.txt") || die "Couldn't open file file.txt, $!";

下表列出了不同模式的可能值

序號 實體和定義
1

< 或 r

只讀訪問

2

> 或 w

建立、寫入和截斷

3

>> 或 a

寫入、追加和建立

4

+< 或 r+

讀取和寫入

5

+> 或 w+

讀取、寫入、建立和截斷

6

+>> 或 a+

讀取、寫入、追加和建立

Sysopen 函式

sysopen函式類似於主要的open函式,不同之處在於它使用系統open()函式,使用提供的引數作為系統函式的引數:

例如,要開啟檔案進行更新,模擬open中的+<filename格式:

sysopen(DATA, "file.txt", O_RDWR);

或者在更新前截斷檔案:

sysopen(DATA, "file.txt", O_RDWR|O_TRUNC );

您可以使用O_CREAT建立新檔案,使用O_WRONLY以只寫模式開啟檔案,使用O_RDONLY以只讀模式開啟檔案。

如果必須建立PERMS引數,則指定檔案的許可權。預設情況下,它採用0x666

下表列出了MODE的可能值。

序號 實體和定義
1

O_RDWR

讀寫

2

O_RDONLY

只讀

3

O_WRONLY

只寫

4

O_CREAT

建立檔案

5

O_APPEND

追加到檔案

6

O_TRUNC

截斷檔案

7

O_EXCL

如果檔案已存在則停止

8

O_NONBLOCK

非阻塞可用性

Close 函式

要關閉檔案控制代碼,從而取消檔案控制代碼與相應檔案的關聯,可以使用close函式。這將重新整理檔案控制代碼的緩衝區並關閉系統的檔案描述符。

close FILEHANDLE
close

如果沒有指定FILEHANDLE,則它將關閉當前選擇的檔案控制代碼。只有在成功重新整理緩衝區並關閉檔案時,它才返回true。

close(DATA) || die "Couldn't close file properly";

讀取和寫入檔案

開啟檔案控制代碼後,您需要能夠讀取和寫入資訊。有多種不同的方法可以將資料讀入和寫入檔案。

<FILEHANDL> 運算子

從開啟的檔案控制代碼讀取資訊的主要方法是<FILEHANDLE>運算子。在標量上下文中,它從檔案控制代碼返回一行。例如:

#!/usr/bin/perl

print "What is your name?\n";
$name = <STDIN>;
print "Hello $name\n";

在列表上下文中使用<FILEHANDLE>運算子時,它將返回指定檔案控制代碼中的一行列表。例如,要將檔案中的所有行匯入到陣列中:

#!/usr/bin/perl

open(DATA,"<import.txt") or die "Can't open data";
@lines = <DATA>;
close(DATA);

getc 函式

getc函式從指定FILEHANDLE或STDIN(如果沒有指定)返回單個字元:

getc FILEHANDLE
getc

如果發生錯誤,或者檔案控制代碼位於檔案末尾,則返回undef。

read 函式

read函式從緩衝的檔案控制代碼讀取一塊資訊:此函式用於從檔案讀取二進位制資料。

read FILEHANDLE, SCALAR, LENGTH, OFFSET
read FILEHANDLE, SCALAR, LENGTH

讀取的資料長度由LENGTH定義,如果未指定OFFSET,則資料將放置在SCALAR的開頭。否則,資料將放置在SCALAR中OFFSET位元組之後。該函式在成功時返回讀取的位元組數,在檔案末尾返回零,如果發生錯誤則返回undef。

print 函式

對於用於從檔案控制代碼讀取資訊的所有不同方法,寫入資訊的主要函式是print函式。

print FILEHANDLE LIST
print LIST
print

print函式將LIST的計算值列印到FILEHANDLE,或列印到當前輸出檔案控制代碼(預設為STDOUT)。例如:

print "Hello World!\n";

複製檔案

這是一個示例,它開啟一個現有的檔案file1.txt並逐行讀取它,然後生成另一個副本檔案file2.txt。

#!/usr/bin/perl

# Open file to read
open(DATA1, "<file1.txt");

# Open new file to write
open(DATA2, ">file2.txt");

# Copy data from one file to another.
while(<DATA1>) {
   print DATA2 $_;
}
close( DATA1 );
close( DATA2 );

重新命名檔案

這是一個示例,它演示瞭如何將檔案file1.txt重新命名為file2.txt。假設檔案位於/usr/test目錄中。

#!/usr/bin/perl

rename ("/usr/test/file1.txt", "/usr/test/file2.txt" );

此函式renames接受兩個引數,它只是重新命名現有檔案。

刪除現有檔案

這是一個示例,它演示瞭如何使用unlink函式刪除檔案file1.txt。

#!/usr/bin/perl

unlink ("/usr/test/file1.txt");

在檔案中定位

您可以使用tell函式來了解檔案的當前位置,並使用seek函式來指向檔案內的特定位置。

tell 函式

第一個要求是在檔案中找到您的位置,您可以使用tell函式:

tell FILEHANDLE
tell

如果指定了FILEHANDLE,則返回檔案指標在FILEHANDLE中的位元組位置;如果沒有指定,則返回當前選擇的預設檔案控制代碼的位置。

seek 函式

seek函式將檔案指標定位到檔案內指定的位元組數:

seek FILEHANDLE, POSITION, WHENCE

該函式使用fseek系統函式,您可以根據三個不同的點進行定位:開頭、結尾和當前位置。您可以透過為WHENCE指定一個值來實現。

零將定位設定為相對於檔案的開頭。例如,該行將檔案指標設定為檔案中的第256個位元組。

seek DATA, 256, 0;

檔案資訊

您可以使用一系列統稱為-X測試的測試運算子在Perl中快速測試某些功能。例如,要對檔案的各種許可權進行快速測試,您可以使用這樣的指令碼:

#/usr/bin/perl

my $file = "/usr/test/file1.txt";
my (@description, $size);
if (-e $file) {
   push @description, 'binary' if (-B _);
   push @description, 'a socket' if (-S _);
   push @description, 'a text file' if (-T _);
   push @description, 'a block special file' if (-b _);
   push @description, 'a character special file' if (-c _);
   push @description, 'a directory' if (-d _);
   push @description, 'executable' if (-x _);
   push @description, (($size = -s _)) ? "$size bytes" : 'empty';
   print "$file is ", join(', ',@description),"\n";
}

以下是您可以為檔案或目錄檢查的功能列表:

序號 運算子和定義
1

-A

指令碼啟動時間減去檔案上次訪問時間(以天為單位)。

2

-B

它是二進位制檔案嗎?

3

-C

指令碼啟動時間減去檔案上次inode更改時間(以天為單位)。

3

-M

指令碼啟動時間減去檔案修改時間(以天為單位)。

4

-O

該檔案是否由真實使用者ID擁有?

5

-R

真實使用者ID或真實組是否可以讀取該檔案?

6

-S

該檔案是否是套接字?

7

-T

它是文字檔案嗎?

8

-W

真實使用者ID或真實組是否可以寫入該檔案?

9

-X

真實使用者ID或真實組是否可以執行該檔案?

10

-b

它是塊特殊檔案嗎?

11

-c

它是字元特殊檔案嗎?

12

-d

該檔案是目錄嗎?

13

-e

檔案是否存在?

14

-f

它是普通檔案嗎?

15

-g

該檔案是否設定了setgid位?

16

-k

該檔案是否設定了粘滯位?

17

-l

該檔案是符號連結嗎?

18

-o

該檔案是否由有效使用者ID擁有?

19

-p

該檔案是命名管道嗎?

20

-r

有效使用者或組ID是否可以讀取該檔案?

21

-s

返回檔案大小,零大小=空檔案。

22

-t

檔案控制代碼是由TTY(終端)開啟的嗎?

23

-u

該檔案是否設定了setuid位?

24

-w

有效使用者或組ID是否可以寫入該檔案?

25

-x

當前有效使用者或使用者組ID是否具有該檔案的執行許可權?

26

-z

檔案大小是否為零?

廣告
© . All rights reserved.