官术网_书友最值得收藏!

1.1 使用傳統(tǒng)方式

使用傳統(tǒng)方式可以訪問文件和路徑,對文本文件和二進制文件進行讀寫。最常用的函數和命令如下。

 Dir:用于列舉路徑下的文件和子文件夾名稱。

 GetAttr和SetAttr:獲取和設置屬性。

 FileCopy、Name、MkDir等:對文件和路徑復制、移動等。

 Open...Write...Close:對文本文件、二進制文件進行打開、讀寫、關閉。

1.1.1 獲取文件或路徑的屬性

右擊文件、文件夾,在彈出菜單中選擇屬性命令,打開屬性窗口后,可以設置只讀屬性和隱藏屬性等。

GetAttr函數用來獲取和判斷文件或路徑的屬性,該函數的參數是一個路徑字符串,返回值是由多個2的整數冪的組合相加的總和,如表1-1所示。

表1-1 文件、路徑的屬性常量

這里假定磁盤下的TE.txt文本文件已設置為“只讀”并且“隱藏”,如圖1-1所示。

圖1-1 查看文件屬性

此時,GetAttr("C:\temp\abcd\TE.txt")會返回一個整數35。其實,35=32(vbArchive)+2(vbHidden)+1(vbReadOnly)。

因此,把GetAttr函數的計算結果拆分為多個枚舉常量值之和,就可以得知該文件的屬性。

下面的過程用來把任何一個正整數拆分為多個2的乘方。

運行上述過程,可以看到13被拆分為8+4+1。根據這個思路,可以設計一個用來判斷文件是否被設置為只讀的自定義函數。

這個函數的原理就是把GetAttr的結果拆分為多個數字,拆分的過程中,看看是否有一個拆分恰好等于枚舉常量vbReadOnly,如果有就提前退出函數,返回True。

運行Debug.Print IsReadOnly("C:\temp\abcd\TE.txt"),在立即窗口返回結果True,表明這是一個只讀文件。

同理,把上述函數中的ReadOnly這個單詞替換為Hidden,就形成了可以判斷文件或路徑是否設置了隱藏屬性。

這里假定C:盤下的Build文件夾被設置了隱藏屬性,那么Debug.Print IsHidden("C:\Build\")返回結果True。

下面的函數可以判斷一個路徑是否為文件夾。

Debug.Print IsDirectory("C:\Build\")返回True。Debug.Print IsDirectory("C:\Build\Hello.csv")返回False。

1.1.2 設置文件或路徑的屬性

與GetAttr相對應的函數是SetAttr,該函數可以設置文件、路徑的屬性。

    SetAttr "C:\Build\", vbHidden + vbReadOnly

這條代碼把Build文件夾的屬性設置為只讀,并且隱藏。

    SetAttr "C:\Build\", vbNormal

這句代碼去掉只讀和隱藏屬性,恢復為正常屬性。

1.1.3 判斷文件或路徑是否存在

使用Dir函數可以列舉出當前路徑下所有文件和子文件夾的名稱,從而間接地判斷一個文件或文件夾是否存在。

Dir函數的語法為:

    Dir(PathName,Attributes)

PathName是一個用來描述文件、路徑的字符串,可以使用*、?通配符。Attributes可以使用如表1-2所示的值。

表1-2 Dir函數用的篩選常量

如果不規(guī)定Attributes屬性,則默認為vbNormal。

代碼分析:如果計算機中不存在Test.txt這個文件,那么Dir函數會返回空字符串;如果文件存在,則返回第一個符合模式的文件名稱(不包含所在路徑),據此可以判斷磁盤或文件夾中是否有某個文件。此外,還可以使用Dir函數判斷是否有某磁盤分區(qū),或者是否有某個文件夾。

如果上述過程中的Path賦值為Path="M:"或者Path="M:\",則可以用來判斷是否存在M:盤。

如果要判斷是否存在某文件夾(路徑),結尾必須加反斜杠。例如Dir("C:\build")用來判斷C:盤下是否有build這個文件,而Dir("C:\build\")用來判斷C盤下是否有build文件夾。

1.1.4 遍歷文件和子文件夾

利用Dir函數和不帶參數的Dir,可以遍歷一個路徑下的所有文件和子文件夾的名稱。現在假定C:\CTEX文件夾中的內容如圖1-2所示。

圖1-2 文件夾中的內容

可以看到有7個子文件夾,4個文件。運行如下的過程,打印出所有的子文件夾名稱和文件名稱。

上述程序的打印結果如圖1-3所示。

可以看出,第一行打印出一個小數點,第二行打印出兩個小數點,從第三行起才是正式的內容。

如果把代碼中的Path = Dir(parent, vbDirectory)修改為Path = Dir(parent),則只遍歷文件,不遍歷子文件夾。

那么如何只遍歷子文件夾呢?這就需要在循環(huán)體中加入If語句來選擇性地遍歷。

圖1-3 遍歷子文件夾和文件

上述過程中,用集合Col來裝載所有的文件和子文件夾的名稱,最后,遍歷Col的時候,首先過濾出所有的子文件夾,然后排除小數點,最后輸出純粹的子文件夾,共7個,如圖1-4所示。

如果要遍歷C:\Ctex下面的所有擴展名為.txt的文本文件,代碼可以修改為如下形式。

圖1-4 只列舉子文件夾名稱

注意,Dir函數中用到了通配符,*.txt可以匹配所有的文本文件,如圖1-5所示。

圖1-5 只遍歷文本文件

1.1.5 文件的復制、移動和刪除

文件的復制、移動和刪除操作,分別用FileCopy、Name As和Kill語句。

FileCopy的語法為:

    FileCopy Source, Destination

Source表示原文件,Destination表示復制的目標。

例如FileCopy Source:="C:\temp\a.xlsx", Destination:="D:\dist\goal.xlsx",表示把文件C:\temp\a.xls復制到D:\dist文件夾下,并且重命名為goal.xlsx。

文件的移動操作就是文件的剪切,也可以理解為文件的重命名。與復制文件的區(qū)別是,原文件不在原位置了。

Name "C:\temp\a.xlsx" As "D:\dist\b.xlsx",就相當于把a文件從原位置剪切到D:\dist文件夾中,并且設置名稱為b.xlsx。

注意 針對文件的移動操作,如果D:\dist\下面原先就有一個b.xlsx文件,那么運行上述的Name語句會導致出錯。也就是說,必須保證目標文件夾中還沒有這個文件,才能進行移動操作。

Kill語句用于刪除文件,如果文件處于打開、占用狀態(tài),運行該語句會出錯。另外,用Kill語句刪除掉的文件,不能通過回收站還原,要謹慎操作。

圖1-6所示的代碼連續(xù)兩次刪除同一個文件,第一句不會出錯,但是運行到第二句時彈出“文件未找到”的錯誤。

圖1-6 重復刪除同一文件的錯誤

1.1.6 文件夾的創(chuàng)建和刪除

文件夾的創(chuàng)建和刪除分別用MkDir和RmDir語句,Mk是Make的縮寫,Rm是Remove的縮寫。

MkDir語句的語法很簡單。

MkDir Path:="C:\temp\2017",會在temp文件夾下創(chuàng)建一個名為2017的文件夾。

RmDir語句用來刪除一個空文件夾。

RmDir Path:="C:\temp\picture",表示刪除picture文件夾,如果該文件夾不是空的,包含其他的文件和子文件夾,那么RmDir會提示錯誤,如圖1-7所示。

也就是說,要刪除一個文件夾,必須先把里面的內容清空后,才能使用RmDir語句刪除。

文件夾的重命名也使用Name…As語句。例如Name "C:\temp\picture" As "C:\temp\pic",表示把文件夾picture重命名為pic。

圖1-7 文件夾中有內容則不能刪除

1.1.7 文本文件的讀寫

編程過程中,經常需要把程序運行的結果數據保存到文本文件,也需要從文本文件中讀取數據供程序使用,這就涉及文本文件的讀寫操作了。

本節(jié)介紹一下用于文件讀寫的Open語句。

Open語句的語法如下。

    Open textFile For mode As fileNum

參數textFile是一個表示文本文件路徑的字符串。

參數mode表示Open語句的讀寫模式,使用最多的模式如下。

 Append:追加模式。

 Output:擦寫模式。

 Input:讀取模式。

如果要把程序運行的結果輸出到文本文件中,那么使用Append模式會把輸出結果追加到文件已有內容之后,而使用Output模式,則會先清空文件原先的內容,再寫入輸出結果。

如果要從文本文件中讀取內容,而不破壞文件,可以使用Input模式。

要注意的是,在使用Output或Append模式時,如果計算機中textFile文件不存在,則會自動創(chuàng)建一個文本文件;如果使用Input模式讀取一個文本文件,文本文件不存在會導致出錯。

參數fileNum是一個文件號,可以是#1到#511中的任何一個。讀寫文件操作結束后,一定要用Close fileNum關閉文件。

下面講述一下導出數據到文本文件中的方法。

上述過程把三個字符串寫入文本文件中,使用Print語句寫入時,在末尾自動換行,如圖1-8所示。

使用Print在同一行輸出多個字符串時,每個字符串之間用半角分號隔開。

上述程序的運行結果如圖1-9所示。

圖1-8 向文件寫入內容

圖1-9 同一行輸出多個結果

除了使用Print語句輸出外,還可以使用Write語句輸出內容到文本文件。

程序的運行結果如圖1-10所示。

可以看出文本文件中的內容都帶有雙引號,這和Print語句有很大不同。

如果把Open "C:\temp\abc.txt" For Output As #1這句中的Output換成Append,則每次寫入文件時,不刪除文件原有內容。請讀者自行測試。

接下來講述如何從已有文本文件中讀取內容,供程序調用。

讀入文件內容涉及的常用術語有:

 v=Input(c,fileNum),表示從文件當前位置讀取c個字符,賦給字符串變量v。

圖1-10 使用Write輸出內容

 Seek fileNum, c,把當前位置重設為c,c的最小值是1。

 LOF(fileNum),返回文件的長度,也就是文件中字符總數。

 EOF(fileNum),返回一個布爾值,當讀取到文件尾部,返回True。經常使用EOF來判斷是否讀取完成。

現在假設文本文件auto.txt中的內容如圖1-11所示。

圖1-11 文本文件內容

代碼分析:a = Input(1, #1),表示從文件的開頭處讀取1個字符,賦給a,因此變量a的取值為字符串h。

b = Input(2, #1),表示從上次讀取的位置起,讀入2個字符賦給變量b,因此b的取值為el。以此類推。

Seek #1, 1表示把讀取位置重設為1,也就是文件開頭,接下來d = Input(3, #1)表示從文件開頭處讀取3個字符,因此d的取值為Hel。

上述程序的運行結果如圖1-12所示。

圖1-12 從文件中讀取字符

根據這個特點,可以把文本文件中的所有字符分發(fā)到字符串數組中。

代碼分析:上述過程,打開文本文件后,根據文件字符總數重新定義數組的上下界,使得數組能恰好容納文本中的字符,然后使用For循環(huán),遍歷文本文件中的每個字符,并分發(fā)到數組的每個元素。

運行到Stop那句,通過本地窗口可以清晰地看到數組s的各元素取值情況,如圖1-13所示。

圖1-13 本地窗口查看數組

可以看出,每個元素恰好取得文件中的一個字符。最后通過Join把數組用*重新連接并輸出,如圖1-14所示。

圖1-14 數組連接為字符串

此外,還可以使用Line Input語句,每次讀取一整行。

假設文件b.txt中有4行古詩,下面用Line Input讀取內容。

代碼分析:本例直接把讀取到的每行打印到立即窗口,因此可以使用Do循環(huán),利用EOF函數來判斷是否讀到文件尾部,如果到了尾部,就結束循環(huán)。

上述程序的運行結果如圖1-15所示。

圖1-15 使用Line Input讀取內容

如果要一次性讀取文本文件的所有內容,可以使用下面的自定義函數。

運行下面的Test過程,即可把文件中的所有內容打印到立即窗口。

上述代碼的源文件為“實例文檔01.xlsm”。

主站蜘蛛池模板: 西贡区| 安国市| 神木县| 东海县| 内黄县| 甘南县| 松原市| 连州市| 田阳县| 微山县| 凉城县| 县级市| 来安县| 常宁市| 新沂市| 遂川县| 叶城县| 嘉义县| 兴安盟| 永顺县| 盘锦市| 东安县| 邵阳县| 壤塘县| 将乐县| 繁昌县| 南溪县| 方城县| 西藏| 九台市| 娱乐| 神农架林区| 克拉玛依市| 贞丰县| 张家港市| 三台县| 哈巴河县| 西贡区| 沂水县| 临猗县| 卢氏县|