【轉(zhuǎn)】MATLAB中textread和textscan的用法和區(qū)別
本文原文摘至此博客?https://www.cnblogs.com/zsgyx/p/10527327.html 感謝總結(jié)。
1.基本語(yǔ)法
textscan的基本語(yǔ)法是:
C = textscan(fid, 'format')
C = textscan(fid, 'format', N)
其中fid為fopen命令返回的文件標(biāo)識(shí)符,這也是和textread的最大不同之處,需要注意的一點(diǎn)是,fid類(lèi)似一個(gè)指針,其指向的位置會(huì)隨著textscan的操作而改變,每讀取一次數(shù)據(jù),它的位置就會(huì)指向你已經(jīng)讀過(guò)的那個(gè)數(shù)據(jù)的后面。format實(shí)際上就是一個(gè)字符串變量,表示讀取數(shù)據(jù)及數(shù)據(jù)轉(zhuǎn)換的規(guī)則。N為按照讀取格式format讀取的次數(shù)。
textread的基本語(yǔ)法是:
? ? [A,B,C,…] = textread(filename,format)
? ? [A,B,C,…] = textread(filename,format,N)
其中filename就是文件名, format就是要讀取的格式,A,B,C就是從文件中讀取到的數(shù)據(jù)。
必須嚴(yán)格遵守用法不可出現(xiàn)data=textread(filename,format,N)的形式
其中括號(hào)里面變量的個(gè)數(shù)必須和format中定義的個(gè)數(shù)相同。 如果每N行相同格式的數(shù)據(jù),可采用[A,B,C,…] = textread(filename,format,N)的語(yǔ)法,讀取N次。
2.兩者的區(qū)別
可以看出這個(gè)兩個(gè)函數(shù)最大的區(qū)別就是:textread不用先f(wàn)open那個(gè)文件,適用于格式統(tǒng)一的txt文件的一次性大批量讀取。而使用textscan函數(shù)之前需要先用fopen函數(shù)打開(kāi)要讀取的文件并返回句柄fid。
其次textread讀取某個(gè)文件后,下次再用textread讀取這個(gè)文件時(shí),還是會(huì)從文件頭開(kāi)始讀取。而textscan函數(shù)每次讀完數(shù)據(jù)后,其對(duì)應(yīng)的句柄fid都是指向接下來(lái)要讀數(shù)據(jù)的地方,類(lèi)似于C函數(shù)中的文件讀取指針,這樣更方便于讀取文本時(shí)的精確控制。
再次,textscan函數(shù)可以將多組數(shù)據(jù)讀到一個(gè)元胞矩陣中,而textread函數(shù)只能將數(shù)據(jù)分別讀取到不同的向量中。比如一個(gè)含有10行3列浮點(diǎn)數(shù)的文件,textscan函數(shù)可以將之讀取到一個(gè)變量名A下 A=textscan(fid, '%f%f%f'), 而使用textread函數(shù)必須將之讀入到三個(gè)變量名中? [A,B,C] = textread(filename,'%f%f%f')。
3.幾個(gè)方便的語(yǔ)法
假設(shè)文件myfile.txt 中的內(nèi)容如下
? ? Sally Type1 12.34 45 Yes
? ? Joe Type2 23.54 60 No
? ? Bill Type1 34.90 12 No
3.1將其分別使用textread 和textscan讀出:
[data1 data2 data3 data4 data5] = textread('myfile.txt','%s%s%f%d%s');使用textread函數(shù)分別將數(shù)據(jù)按照格式讀入到data1—data5中。然后可使用賦值語(yǔ)句data=[data1 data2 data3 data4 data5 data6]生成一個(gè)二維數(shù)組data。
fid = fopen('myfile.txt');
C = textscan(fid, '%s%s%f%d%s');
fclose(fid);使用textscan函數(shù)讀取文件,輸出C為1*5的細(xì)胞數(shù)組,每個(gè)數(shù)組中存放每列的數(shù)據(jù)
3.2如果只讀取第一列的數(shù)據(jù),可使用如下語(yǔ)句:
[names]=textread('myfile.txt','%s%*[^n]');
%*[^n] 表示從當(dāng)前直接跳到行尾,而使用%[^n]則表示一直讀到行尾,% *是一個(gè)跳過(guò)符號(hào),表示跳過(guò)該位。例如在讀取上述文件過(guò)程中只讀取浮點(diǎn)數(shù)的整數(shù)位,可使用如下兩種語(yǔ)句,將小數(shù)點(diǎn)在內(nèi)的小數(shù)部分看作浮點(diǎn)數(shù)或者字符串,讀取是略過(guò)。
[data1 data2 data3 data4 data5] = textread('myfile.txt','%s%s-%*f%d%s');
或者
[data1 data2 data3 data4 data5] = textread('myfile.txt','%s%s-%*s%d%s');
3.3跳行讀取
另外如果我想略過(guò)若干行之后才開(kāi)始讀取數(shù)據(jù)的話,可以使用headerlines命令定義略過(guò)的行數(shù)。如果數(shù)據(jù)之間不是使用空格作為分隔符的話,可以使用delimiter命令定義各種分隔符。
'headerlines',1,'delimiter',';'
3.4格式化輸出的重復(fù)使用
如果我想讀取文件中70行70列的文件該怎么辦呢? 當(dāng)然我們可以在函數(shù)中format處寫(xiě)上70個(gè)%f,但這樣太麻煩了。有一種簡(jiǎn)單的方法就是使用下面的函數(shù)。
FormatString=[repmat(' %f',1,70)];?
ez = cell2mat(textscan(f1,FormatString,70,'HeaderLines',3));
第一句話表示定義一個(gè)含有70個(gè)%f的字符串(repmat(A,m,n),repmat為復(fù)制函,將A復(fù)制成m×n的矩陣),即將%f復(fù)制成1行70列。對(duì)于字符串‘%f’的復(fù)制,每行都是在一個(gè)字符串組呢,如repmat(‘%f’,1,3) ->‘%f%f%f’。
第二句話的意思是 將此字符串作為讀取格式,按照這個(gè)格式讀取70次,并忽略文件中的前三行。 由于textscan只是把數(shù)據(jù)讀到了一個(gè)元胞數(shù)組中了,需要使用cell2mat函數(shù)將這里面的所有 cell組合成一個(gè)數(shù)組。