ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Java NIO
    Java 2020. 2. 6. 09:39
    반응형

    Java NIO(JDK 1.4 ~)

    JDK 1.4 ~ NIO(New IO) 추가

    추가된 이유 : 속도때문

    Stream을 사용하지 않고 Channel과 Buffer를 사용

    Channel

    간단하게 객체만 생성하여 read()나 write(), close() 메서드만 불러주면 됨

    중간에서 처리하는 도매상같은 것

    Buffer 

    도매상에서 물건을 사고, 소비자에게 물건을 파는 소매상 같은 것

    예제

    package study;
    
    import java.io.FileInputStream;
    import java.io.FileOutputStream;
    import java.nio.ByteBuffer;
    import java.nio.channels.FileChannel;
    
    public class NIOTest {
        public static void main(String[] args) {
            NIOTest test = new NIOTest();
            test.basicWriteAndRead();
        }
    
        public void basicWriteAndRead() {
            String fileName = "/Users/hs/test.txt";
            try {
                writeFile(fileName, "My Name is Jamie");
                readFile(fileName);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    
        public void writeFile(String fileName, String data) throws Exception {
        	// 파일을 쓰기위한 FileChannel 객체 생성 - FileOutputStream(파일명).getChannel()
            FileChannel channel = new FileOutputStream(fileName).getChannel();
            byte[] byteData = data.getBytes();
            // ByteBuffer의 static wrap(저장할 Byte배열) 메서드 호출시 ByteBuffer 객체 생성
            ByteBuffer buffer = ByteBuffer.wrap(byteData);
            // FileChannel의 write()메서드에 buffer를 넘겨주면 파일에 쓰게 됨
            channel.write(buffer);
            // 채널 닫음
            channel.close();
        }
    
        public void readFile(String fileName) throws Exception {
        	// 파일을 읽기위한 FileChannel 객체 생성 - FileInputStream(파일명).getChannel()
            FileChannel channel = new FileInputStream(fileName).getChannel();
            // ByteBuffer의 static allocate(데이터 저장크기) 메서드 호출시 buffer 객체 생성 가능
            ByteBuffer buffer = ByteBuffer.allocate(1024);
            // FileChannel의 read()메서드에 buffer를 넘겨주면 데이터를 해당 버퍼에 담음
            channel.read(buffer);
            // buffer에 담겨있는 데이터의 가장 앞으로 이동 (위치 찍고 되감기)
            buffer.flip();
            // 데이터가 더 남아있는지 확인 - 위치찍은곳까지
            while(buffer.hasRemaining()) {
            	// get()으로 데이터를 한 바이트씩 읽음
                System.out.print((char)buffer.get());
            }
            // 채널 닫음
            channel.close();
        }
    }
    
    ////////////////////////////////////////////////////////////////////
    My Name is Jamie
    Process finished with exit code 0
    

    NIO의 Buffer 클래스

    java.nio.Buffer 클래스를 확장하여 사용

    종류

    ByteBuffer / CharBuffer / DoubleBuffer / FloatBuffer / IntBuffer / LongBuffer / ShortBuffer 등

    버퍼의 상태 및 속성을 확인하기 위한 메서드

    // 버퍼에 담을 수 있는 크기 리턴
    int capacity()
    
    // 버퍼에서 읽거나 쓸 수 없는 첫 위치 리턴
    int limit()
    
    // 현재 버퍼의 위치 리턴
    int position()
    
    /* 관계
     * 0 <= position() <= limit() <= capacity()
     */

    위치를 변경하는 메서드

    // limit 값을 현재 position으로 지정 후 position을 0으로 이동(가장 앞)
    Buffer flip()
    
    // 현재 position을 mark
    Buffer mark()
    
    // 버퍼의 position을 mark 한 곳으로 이동
    Buffer reset()
    
    // 현재 버퍼의 position을 0으로 이동 - flip()과 달리 limit 값을 변경하지 않음
    Buffer rewind()
    
    // limit-position 계산 결과를 리턴 - limit까지 읽음
    int remaining()
    
    // position과 limit 값이 다를 경우 true 리턴 - limit까지 읽음
    boolean hasReamaining()
    
    // 버퍼를 지우고 현재 position을 0으로 이동하며, limit 값을 버퍼의 크기로 변경
    Buffer clear()

    예제

    package study;
    
    import java.nio.IntBuffer;
    
    public class BufferTest {
    
        public static void main(String[] args) {
            BufferTest test = new BufferTest();
            test.checkBuffer();
        }
        public void printBufferStatus(String job, IntBuffer buffer) {
            System.out.println("Buffer " + job + " !!!");
            System.out.format("Buffer position=%d remaining=%d limit=%d\n",
                    buffer.position(), buffer.remaining(), buffer.limit());
        }
    
        public void checkBuffer() {
            try {
                IntBuffer buffer = IntBuffer.allocate(1024);
                for(int loop = 0; loop < 10; loop++) {
                    buffer.put(loop);
                }
                System.out.println("Buffer capacity = " + buffer.capacity());
                System.out.println("Buffer limit    = " + buffer.limit());
                System.out.println("Buffer position = " + buffer.position());
                buffer.flip();
                System.out.println("Buffer flipped !!!");
                System.out.println("Buffer limit    = " + buffer.limit());
                System.out.println("Buffer position = " + buffer.position());
                System.out.println("--------------------------");
                buffer.get();
                printBufferStatus("get", buffer);
                buffer.mark();
                printBufferStatus("mark", buffer);
                buffer.get();
                printBufferStatus("get", buffer);
                buffer.reset();
                printBufferStatus("reset", buffer);
                buffer.rewind();
                printBufferStatus("rewind", buffer);
                buffer.clear();
                printBufferStatus("clear", buffer);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    ////////////////////////////////////////////////////////////////////////////
    Buffer capacity = 1024
    Buffer limit    = 1024
    Buffer position = 10
    Buffer flipped !!!
    Buffer limit    = 10
    Buffer position = 0
    --------------------------
    Buffer get !!!
    Buffer position=1 remaining=9 limit=10
    Buffer mark !!!
    Buffer position=1 remaining=9 limit=10
    Buffer get !!!
    Buffer position=2 remaining=8 limit=10
    Buffer reset !!!
    Buffer position=1 remaining=9 limit=10
    Buffer rewind !!!
    Buffer position=0 remaining=10 limit=10
    Buffer clear !!!
    Buffer position=0 remaining=1024 limit=1024
    
    Process finished with exit code 0

    예제 2

    반응형

    'Java' 카테고리의 다른 글

    서버 통신 - Socket / UDP  (0) 2020.02.07
    Serializable  (0) 2020.02.07
    JAVA I/O  (0) 2020.02.06
    Thread 관련 - Object, ThreadGroup, ThreadLocal, volatile  (0) 2020.01.16
    Thread Class  (0) 2020.01.15

    댓글

Designed by Tistory.