這裡是在網上找來的幾個關於 IO流檔案的輸入流具體例項程式碼,接下來試著將其解析得更清楚明白一些,希望初學者看完能有所收穫,這篇這個例子的程式碼是把檔案上的字元讀取給字元組後,一組一組輸出
方法/步驟
網上找來的例項
import java.io.*;
public class ReadFile
{
public static void readFileByChars(String fileName) {
File file = new File(fileName);
Reader reader = null;
try {
char[] tempchars = new char[10];
int charread = 0;
reader = new InputStreamReader(new FileInputStream(fileName));
while ((charread = reader.read(tempchars)) != -1) {
if ((charread == tempchars.length)&& (tempchars[tempchars.length - 1] != '\r')) {
System.out.print(tempchars);
} else {
for (int i = 0; i < charread; i++) {
if (tempchars[i] == '\r') {
continue;
} else {
System.out.print(tempchars[i]);
}
}
}
}
} catch (Exception e1) {
e1.printStackTrace();
} finally {
if (reader != null) {
try {
reader.close();
} catch (IOException e1) {
}
}
}
}
public static void main(String args[]) throws IOException
{
String path="D:\\f.txt";
ReadFile rf=new ReadFile();
rf.readFileByChars(path);
}
}
同時在D盤根目錄新建一個f.txt檔案
內容為:
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零
一二三四五六七八九十零一二三四五六七八九十零一二三四五六七八九十零
關於部分程式碼的講解可以參考上篇的內容,兩者例子的程式碼有相同之處,我們下面直接講解 while迴圈內的程式碼
0 java IO流檔案的輸入流具體例項解析(一)
while ((charread = reader.read(tempchars)) != -1)
charread 是上面定義的整型變數, tempchars是上面定義的字元組,儲存個數是10,reader.read(tempchars)和(一)篇的reader.read()有較大不一樣,
首先reader.read(tempchars)一次讀取多個字元,並直接賦值給tempchars這個字元組, tempchars儲存個數是10,如果檔案有多於10個字元可讀取,那就讀取30個,剩下的下次讀取。
然後reader.read(tempchars)返回的值是讀取字元的個數,如果讀了10個字元,就返回10,讀了5個,就返回5。
reader.read(tempchars)讀到檔案結尾時,也是返回-1。
所以條件的意識就是讀取一組字元,並返回讀取字元的個數賦給charread,讀到檔案尾時就為false結束迴圈
if ((charread == tempchars.length)&&
(tempchars[tempchars.length - 1] != '\r'))
tempchars.length就是字元組的定義長度,即10,
tempchars[tempchars.length - 1]即tempchar[9],
這條件有兩個子條件,
第一是讀取的個數charread必須要等於字元組的定義長度,即把字元組裝滿
第二是字元組的最後一個字元不能是'\r'
為什麼要設定如此一個條件呢,首先要理解\r是什麼
'\r'是換行字元,'\n'也可以換行
windows檔案換行結尾是\r\n這兩字元,讀取檔案時也會一起讀進來,如果這個兩個字元一起輸出或者連續輸出是換一行,但如果分開不連續輸出就是換兩行
但是在其他編譯環境例如unix,mac, \r\n就是換兩行,
所以我們為了相容,要把\r\n這兩個其中一個遮蔽掉,這裡的條件就是為這裡設定的
所以這個條件是測試是不是到了行的末尾的,當然前提是檔案的內容只有一行
如果檔案的內容只有一行,而且這一行非常的長,這個條件就可以測試是不是到了行的結尾,如果是false,就是到了行的結尾了,要執行else的語句了
但是如果檔案的內容有非常多的行,像我建立的檔案那樣,這樣這個方法就是沒有用的,而且沒有意義
else {
for (int i = 0; i < charread; i++) {
if (tempchars[i] == '\r') {
continue;
} else {
System.out.print(tempchars[i]);
}
}
}
當字元組的最後一個字元是\r或者最後的不足10個字元的時候,就會執行這個else語句,把tempchars[i]字元組的字元一個個檢測,不是'\r'就輸出,是'\r'就說明到了檔案尾,就不執行迴圈輸出字元了,continue英文是繼續的意思,在這裡程式碼的意思是結束這一次while迴圈的意思
到此,我們就while裡面的程式碼講完了,為了進一步理解程式碼,我們修改一下程式碼,加上四行程式碼:
在 int charread = 0;這行下加
int a=0;
在 System.out.print(a++);
}
}
} 這行下加
System.out.print('f');
在if (tempchars[i] == '\r') {這行下加
System.out.print('a');
在System.out.print(tempchars[i]);這行下加
System.out.print(a++);
看輸出結果
結果是:
一二三四五六七八九十f零
一二三四五六七f八九十零
一二三四f五六七八九十零
一f二三四五六七八九十零f
一二三四五六七八f九十零
一二三四五f六七八九十零
一二f三0四1五2六3七4八5九6十7零8af
一二三四五六七八九f十零一二三四五六七八f九十零一二三四五六七f八9九10十11零12f
f代表一次while迴圈的結束,a表示執行了continue;語句,123這些數字表示System.out.print(tempchars[i]);的執行次數
輸出的結果得出幾個結論:
第一,在檔案的最後一個字元是\r,但不會被讀進陣列中
第二,除了檔案的最後一行,其他行的末尾都有\r\n這兩個字元,而且\r幾乎都沒刪除,因為只出現了一個a,而每兩個f之間可見只有八個字元,但我們設定的字元組有10位長度,剩下的倆個字元應該是\r\n
第三,程式碼沒能力排除多行檔案的\r,甚至會造成不規律的多一行情況,因為只出現了一次a,而且不是在最後出現
最後的最後改良一下程式碼while迴圈改為
while ((charread = reader.read(tempchars)) != -1) {
inner:
for (int i = 0; i < charread; i++) {
if (tempchars[i] == '\r') {
System.out.print('a');
continue inner;
} else {
System.out.print(tempchars[i]);
}
}
System.out.print('f');
}
有兩行 System.out.print('a');System.out.print('f');是多餘,用了檢測程式碼執行情況的
結果是
一二三四五六七八九十f零a
一二三四五六七f八九十零a
一二三四f五六七八九十零a
一f二三四五六七八九十零fa
一二三四五六七八f九十零a
一二三四五f六七八九十零a
一二f三四五六七八九十零af
一二三四五六七八九f十零一二三四五六七八f九十零一二三四五六七f八九十零f
從結果來看每行末尾/r都沒有輸出