zz - Java 流(Stream)簡(jiǎn)介:1、基本的輸入流和輸出流
原作者為csdn上的 YidingHehttp://blog.csdn.net/YidingHe
本人打算寫(xiě)幾篇文章,介紹一下流。本文是針對(duì)初學(xué)者的,加上本人水平有限,所以不敢說(shuō)寫(xiě)得很高深。如果你是初學(xué)者,而且對(duì)流這個(gè)東西很頭疼,你就應(yīng)該看看這個(gè)。
本文發(fā)表在:http://blog.csdn.net/YidingHe,轉(zhuǎn)載請(qǐng)保留出處。
流是 Java 中最重要的基本概念之一。文件讀寫(xiě)、網(wǎng)絡(luò)收發(fā)、進(jìn)程通信,幾乎所有需要輸入輸出的地方,都要用到流。
流是做什么用的呢?就是做輸入輸出用的。為什么輸入輸出要用“流”這種方式呢?因?yàn)槌绦蜉斎胼敵龅幕締挝皇亲止?jié),輸入就是獲取一串字節(jié),輸出就是發(fā)送一串字節(jié)。但是很多情況下,程序不可能接收所有的字節(jié)之后再進(jìn)行處理,而是接收一點(diǎn)處理一點(diǎn)。比方你下載魔獸世界,不可能全部下載到內(nèi)存里再保存到硬盤(pán)上,而是下載一點(diǎn)就保存一點(diǎn)。這時(shí),流這種方式就非常適合。
在 Java 中,每個(gè)流都是一個(gè)對(duì)象。流分為兩種:輸入流(InputStream)和輸出流(OutputStream)。對(duì)于輸入流,你只要從流當(dāng)中不停地把字節(jié)取出來(lái)就是了;而對(duì)于輸出流,你只要把準(zhǔn)備好的字節(jié)串傳給它就行。
______________Java 程序____________
| |
外部系統(tǒng) --|--(輸入流)--> 處理邏輯 --(輸出流)---|--> 外部系統(tǒng)
|_________________________________|
流對(duì)象是怎么獲得的呢?不同的外部系統(tǒng),獲取流的方式也不同。例如,文件讀寫(xiě)就要?jiǎng)?chuàng)建 FileInputStream/FileOutputStream 對(duì)象,而網(wǎng)絡(luò)通信是通過(guò) Socket 對(duì)象來(lái)獲取輸入輸出流的。一般來(lái)說(shuō),如果一個(gè)類(lèi)有 getInputStream() 或 getOutputStream() 這樣的方法,就表明它是通過(guò)流對(duì)象來(lái)進(jìn)行輸入輸出的。
InputStream 是輸入流,下面是一個(gè)通過(guò) InputStream 讀取文件的例子:
- import java.io.File;
- import java.io.FileInputStream;
- import java.io.IOException;
- import java.io.InputStream;
- import java.io.FileNotFoundException;
- import java.util.Arrays;
- /**
- * 通過(guò)流讀取文件
- */
- public class ReadFileDemo {
- // 程序入口
- public static void main(String[] args) {
- String path = "c:/boot.ini";
- File file = new File(path);
- // 創(chuàng)建輸入流
- InputStream is;
- try {
- is = new FileInputStream(file);
- } catch (FileNotFoundException e) {
- System.err.println("文件 " + path + " 不存在。");
- return;
- }
- // 開(kāi)始讀取
- byte[] content = new byte[0]; // 保存讀取出來(lái)的文件內(nèi)容
- byte[] buffer = new byte[10240]; // 定義緩存
- try {
- int eachTime = is.read(buffer); // 第一次讀取。如果返回值為 -1 就表示沒(méi)有內(nèi)容可讀了。
- while (eachTime != -1) {
- // 讀取出來(lái)的內(nèi)容放在 buffer 中,現(xiàn)在將其合并到 content。
- content = concatByteArrays(content, buffer, eachTime);
- eachTime = is.read(buffer); // 繼續(xù)讀取
- }
- } catch (IOException e) {
- System.err.println("讀取文件內(nèi)容失敗。");
- e.printStackTrace();
- } finally {
- try {
- is.close();
- } catch (IOException e) {
- // 這里的異常可以忽略不處理
- }
- }
- // 輸出文件內(nèi)容
- String contentStr = new String(content);
- System.out.println(contentStr);
- }
- /**
- * 合并兩個(gè)字節(jié)串
- *
- * @param bytes1 字節(jié)串1
- * @param bytes2 字節(jié)串2
- * @param sizeOfBytes2 需要從 bytes2 中取出的長(zhǎng)度
- *
- * @return bytes1 和 bytes2 中的前 sizeOfBytes2 個(gè)字節(jié)合并后的結(jié)果
- */
- private static byte[] concatByteArrays(byte[] bytes1, byte[] bytes2, int sizeOfBytes2) {
- byte[] result = Arrays.copyOf(bytes1, (bytes1.length + sizeOfBytes2));
- System.arraycopy(bytes2, 0, result, bytes1.length, sizeOfBytes2);
- return result;
- }
- }
雖然寫(xiě)得很啰嗦,但這確實(shí)是 InputStream 的基本用法。注意,這只是一個(gè)例子,說(shuō)明如何從輸入流中讀取字節(jié)串。實(shí)際上,Java 提供更簡(jiǎn)單的方式來(lái)讀取文本文件。以后將會(huì)介紹。
相比從流中讀取,使用 OutputStream 輸出則是非常簡(jiǎn)單的事情。下面是一個(gè)例子:
- import java.io.OutputStream;
- import java.io.FileOutputStream;
- import java.io.File;
- import java.io.IOException;
- import java.util.Date;
- /**
- * 將當(dāng)前日期保存到文件
- */
- public class SaveFileDemo {
- public static void main(String[] args) throws IOException {
- String path = "c:/now.txt";
- File file = new File(path);
- if (!file.exists() && !file.createNewFile()) {
- System.err.println("無(wú)法創(chuàng)建文件。");
- return;
- }
- OutputStream os = new FileOutputStream(file); // 創(chuàng)建輸出流(前提是文件存在)
- os.write(new Date().toString().getBytes()); // 將當(dāng)前時(shí)間寫(xiě)入文件
- os.close(); // 必須關(guān)閉流,內(nèi)容才會(huì)寫(xiě)入文件。
- System.out.println("文件寫(xiě)入完成。");
- }
- }
Java 還提供其它的流操作方式,但它們都是對(duì) InputStream 和 OutputStream 進(jìn)行擴(kuò)展或包裝。所以這兩個(gè)類(lèi)是基礎(chǔ),必須要理解它們的使用。
posted on 2012-03-02 20:20 rosial 閱讀(290) 評(píng)論(0) 編輯 收藏 所屬分類(lèi): 技術(shù)轉(zhuǎn)帖留存