athrunwang

          紀元
          數據加載中……
          關于NIO對文件讀寫的簡單總結

          本篇主要介紹的是關于nio在文件讀寫方面的簡單應用,具體底層實現原理,并未深究。

          新的輸入/輸出(NIO)庫是在JDK 1.4中引入的。它與原來的I/O庫最重要的區別是數據打包和傳輸的方式的不同,原來的 I/O 的方式處理數據,而 NIO 的方式處理數據。按塊處理數據比按(流式的)字節處理數據要快得多。但是面向塊的I/O缺少一些面向流的I/O所具有的優雅性和簡單性。

          示例代碼:使用IONIO讀取一個文件中的內容

           1import java.io.FileInputStream;
           2import java.io.IOException;
           3import java.nio.ByteBuffer;
           4import java.nio.channels.FileChannel;
           5
           6public class Test {           
           7    /**  
           8     * 使用IO讀取指定文件的前1024個字節的內容。  
           9     * @param file 指定文件名稱。  
          10     * @throws java.io.IOException IO異常。  
          11     */
           
          12    public static void ioRead(String file) throws IOException{
          13        FileInputStream in = new FileInputStream(file);
          14        byte[] b = new byte[1024];
          15        in.read(b);
          16        System.out.println(new String(b));
          17        in.close();
          18    }

          19
          20    /**  
          21     * 使用NIO讀取指定文件的前1024個字節的內容。  
          22     * @param file 指定文件名稱。  
          23     * @throws java.io.IOException IO異常。  
          24     */
           
          25    public static void nioRead(String file) throws IOException{
          26        FileInputStream in = new FileInputStream(file);
          27        FileChannel channel = in.getChannel();
          28
          29        ByteBuffer buffer = ByteBuffer.allocate(1024);
          30        channel.read(buffer);
          31        byte[] b = buffer.array();
          32        System.out.println(new String(b));
          33        channel.close();
          34    }

          35}

          從以上示例代碼中,我們可以看到對于nio非常重要的兩個核心概念:通道與緩沖區。

          1)通道
               Channel是對原I/O包中的流的模擬,可以通過它讀取和寫入數據。拿NIO與原來的I/O做個比較,通道就像是流。
             通道與流的不同之處在于通道是雙向的。而流只是在一個方向上移動(一個流必須是InputStream或者OutputStream的子類), 而通道可以用于讀、寫或者同時用于讀寫。
               因為它們是雙向的,所以通道可以比流更好地反映底層操作系統的真實情況。特別是在UNIX模型中,底層操作系統通道是雙向的。

          2)緩沖區
                 NIO庫中,所有數據都是用緩沖區處理的。在讀取數據時,它是直接讀到緩沖區中的。在寫入數據時,它是寫入到緩沖區中的。任何時候訪問NIO中的數據,您都是將它放到緩沖區中。
             緩沖區實質上是一個數組。通常它是一個字節數組,但是也可以使用其他種類的數組。但是一個緩沖區不僅僅是一個數組。緩沖區提供了對數據的結構化訪問,而且還可以跟蹤系統的讀/寫進程。
             最常用的緩沖區類型是ByteBuffer。 一個ByteBuffer可以在其底層字節數組上進行get/set操作(即字節的獲取和設置)。
             ByteBuffer不是NIO中唯一的緩沖區類型。事實上,對于每一種基本Java類型都有一種緩沖區類型:
             ByteBuffer
             CharBuffer
             ShortBuffer

             IntBuffer
             LongBuffer
             FloatBuffer
             DoubleBuffer
             每一個Buffer類都是Buffer接口的一個實例。 

          文件的讀寫

          nio讀取文件涉及三個步驟:
             (1) FileInputStream獲取Channel。
             (2) 創建Buffer。
             (3) 將數據從Channel讀到Buffer 中。

          文件的寫操作與讀操作類似。

          下面我以文件的拷貝為例,展示一下nio的讀寫過程:

           1import java.io.FileInputStream;
           2import java.io.FileNotFoundException;
           3import java.io.FileOutputStream;
           4import java.io.IOException;
           5import java.nio.ByteBuffer;
           6import java.nio.channels.FileChannel;
           7
           8/**
           9 * 將一個文件的所有內容拷貝到另一個文件中。
          10 * 
          11 * 基本步驟:
          12 * 1.得到輸入輸出通道,創建緩沖區
          13 * 2.從源文件中將數據讀到這個緩沖區中,然后將緩沖區寫入目標文件.此過程需不斷循環直到源文件結束
          14 * 
          15 * @author greatjone
          16 */

          17public class CopyFile {
          18    public static void copy(String file,String copyfile) throws IOException{
          19         // 獲取源文件和目標文件的輸入輸出流
          20        FileInputStream fin = new FileInputStream(file);
          21        FileOutputStream fout = new FileOutputStream(copyfile);
          22
          23        // 獲取輸入輸出通道
          24        FileChannel fcin = fin.getChannel();
          25        FileChannel fcout = fout.getChannel();
          26
          27        // 創建緩沖區
          28        ByteBuffer buffer = ByteBuffer.allocate(1024);
          29
          30        while (true{
          31            // clear方法重設緩沖區,使它可以接受讀入的數據
          32            buffer.clear();
          33
          34            // 從輸入通道中將數據讀到緩沖區
          35            int r = fcin.read(buffer);
          36
          37            // read方法返回讀取的字節數,可能為零,如果該通道已到達流的末尾,則返回-1
          38            if (r == -1{
          39                break;
          40            }

          41            
          42            // flip方法讓緩沖區可以將新讀入的數據寫入另一個通道
          43            buffer.flip();
          44
          45            // 從輸出通道中將數據寫入緩沖區
          46            fcout.write(buffer);
          47        }

          48    }

          49}

          50

           關于nio更加詳細深入研究請參考:http://zhangshixi.javaeye.com/category/101360

          posted on 2012-01-03 17:28 AthrunWang 閱讀(389) 評論(0)  編輯  收藏


          只有注冊用戶登錄后才能發表評論。


          網站導航:
           
          主站蜘蛛池模板: 丘北县| 博湖县| 阜宁县| 丹江口市| 永康市| 仁布县| 介休市| 临清市| 鲁山县| 临澧县| 阳西县| 盐边县| 巫山县| 巴楚县| 怀安县| 临江市| 遵化市| 晋宁县| 湘乡市| 温州市| 涿州市| 普宁市| 金寨县| 阿图什市| 隆子县| 瓦房店市| 图们市| 灌阳县| 栾城县| 确山县| 青龙| 吉林市| 县级市| 玉田县| 金门县| 邹平县| 崇义县| 焦作市| 东乡县| 英山县| 龙口市|