자바에서의 입출력 |
입출력이란?
I/O란 Input과 Output의 약자로 입력과 출력, 간단히 줄여서 입출력이라고 한다. 입출력은 컴퓨터 내부 또는 외부의 장치와 프로그램간의 데이터를 주고받는 것을 말한다.
스트림
- 자바에서 입출력을 수행할때 데이터를 운반하는데 사용되는 연결 통로이다.
- 스트림은 단방향 통신만 가능하다.
- 스트림은 먼저 보낸 데이터를 먼저 받게 되어 있으며 중간에 건너뜀 없이 연속적으로 데이터를 주고 받는다.(FIFO)
- 인터페이스 스트림과 용어는 같지만 다른 개념이다.
바이트기반 스트림 - InputStream, OutputStream
스트림은 바이트단위로 데이터를 전송하며 입출력 대상에 따라 다음과 같은 입출력스트림이 있다.
입력스트림 | 출력스트림 | 입출력 대상의 종류 |
FileInputStream | FileOutputStream | 파일 |
ByteArrayInputStream | ByteArrayOutputStream | 메모리(byte배열) |
PipedInputStream | PipedOutputStream | 프로세스(프로세스간의 통신) |
AudioInputStream | AudioOutputStream | 오디오장치 |
이들은 모두 InputStream, OutputStream의 자손들이며, 각각 읽고 쓰는데 필요한 추상메서드를 자신에 맞게 구현해 놓았다.
InputStream | OutputStream |
abstract int read() | abstract void write(int b) |
int read(byte[] b) | void write(byte[] b) |
int read(bye[] b, int off, int len) | void wrtie(byte[], int off, int len) |
InputStream의 read()와 OutputStream의 write(int b)는 입출력의 대상에 따라 읽고 쓰는 방법이 다를 것이기 때문에 상황에 알맞게 구현할 수 있도록 추상메서드로 정의되어 있다. read()와 write(int b)를 제외한 나머지 메서드들도 read()와 write(int b)를 이용해서 구현되어 있다.
보조 스트림
보조스트림은 실제 데이터를 주고받는 스트림이 아니기 때문에 데이터를 입출력할 수 있는 기능은 없지만, 스트림의 기능을 향상시키거나 새로운 기능을 추가 할 수 있다.
/* 예시 */
//먼저 기반스트림을 생성한다.
FileInputStream fis = new FileInputStream("test.txt");
//기반스트림을 이용해서 보조스트림을 생성한다.
BufferedInputStream bis =new BufferedInputStream(fis);
//보조스트림인 BufferedInputStream으로부터 데이터를 읽는다. 실제로는 FileInputStream이 수행
bis.read();
입력 | 츨력 | 설명 |
FilterInputStream | FilterOutputStream | 필터를 이용한 입출력 처리 |
BufferedInputStream | BufferedOutputStream | 버퍼를 이용한 입출력 성능향상 |
DataInputStream | DataOutputStream | 기본형 단위(Primitive type)로 데이터를 처리하는 기능 |
SequenceInputStream | 없음 | 두 개의 스트림을 하나로 연결 |
LineNumberInputStream | 없음 | 익어 온 데이터의 라인 번호를 카운트(JDK 1.1부터 LineNumberReader로 대체) |
ObjectInputStream | ObjectOutoutStream | 데이터를 객체단위로 읽고 쓰는데 사용 주로 파일을 이용하며 객체 직렬화와 관련 있음 |
없음 | PrintStream | 버퍼를 이용하며, 추가적인 print관련 기능 (print, printf, println메서드) |
pushbackInputStream | 없음 | 버퍼를 이용해서 읽어 온 데이터를 다시 되돌리는 기능 (unread, push back to buffer) |
문자기반 스트림 - Reader, Writer
자바에서는 한 문자를 의미하는 char형이 1 byte가 아니라 2 byte이기 때문에 바이트기반의 스트림으로는 문자를 처리하는 데는 어려움이 있다. 이 점을 보완하기 위해서 문자기반의 스트림이 제공된다.
InputStream -> Reader
OutputStream -> Writer
- 바이트기반 스트림과 문자기반 스트림의 비교
바이트기반 스트림 | 문자기반 스트림 |
FileInputStream FileOutputStream |
FileReader FileWriter |
ByteArrayInputStream ByteArrayOutputStream |
CharArrayReader CharArrayWriter |
PipedInputStream PipedOutputStream |
PipedReader PipedWriter |
StringBufferInputStream(deprecated) StringBufferOutputStream(deprecated) |
StringReader StringWriter |
-바이트기반 스트림과 문자기반 스트림의 읽고 쓰는 메서드 비교
InputStream | Reader |
abstract int read() int read(byte[] b) int read(byte[] b, int off, int len) |
int read() int read(char[] cbuf) abstract int read(char[] cbuf, int off, int len) |
OutputStream | Writer |
abstract void writer(int b) void writer(byte[] b) void write(byte[] b, int off, int len) |
void write(int c) void write(char[] cbuf) abstract void write(char[] cbuf, int off, int len) void write(String str) void write(String str, int off, int len) |
- 바이트기반 보조스트림과 문자기반 보조스트림
바이트기반 보조스트림 | 문자기반 보조스트림 |
BufferedInputStream BufferedOutputStream |
BufferedReader BufferedWriter |
FilterInputStream FilterOutputStream |
FilterReader FilterWriter |
LineNumberInputStream | LineNumberReader |
PrintStream | printWriter |
PushbackInputStream | PushbackReader |
바이트기반 스트림 |
1. 바이트기반 스트림
1) InputStream과 OutputStream
- InputStream의 메서드
메서드명 | 설명 |
int available() | 스트림으로부터 읽어 올 수 있는 데이터의 크기를 반환한다. |
void close() | 스트림을 닫음으로써 사용하고 있던 자원을 반환한다. |
void mark(int readlimit) | 현재위치를 표시해 놓는다. 후에 reset()에 의해서 표시해 놓은 위치로 다시 돌아갈 수 있다. readmit은 되돌아갈 수 있는 byte의 수이다. |
boolean markSupported() | mark()와 reset()을 지원하는지를 알려 준다. mark()와 reset()기능을 지원하는 것은 선택적이므로, mark()와 reset()을 사용하기 전에 markSupported()를 호출해서 지원여부를 확인해야 한다. |
abstract int read() | 1byte를 읽어 온다(0~255사이의 값). 더 이상 읽어 올 데이터가 없으면 -1을 반환한다. abstract메서들서 InputStream의 자손들은 자신의 사황에 알맞게 구현해야한다. |
int read(byte[] b) | 배열 b의 크기만큼 읽어서 배열을 채우고 읽어 온 데이터의 수를 반환한다. 반환하는 값은 항상 배열의 크기보다 작거나 같다. |
int read(byte[], int off, int len) | 최대 len개의 byte를 읽어서, 배열 b의 지정된 위치(off)부터 저장한다. 실제로 읽어 올 수 있는 데이터가 len개보다 적을 수도 있다.) |
void reset() | 스트림에서의 ㅟ치를 마지막으로 mark()이 호출되었던 위치로 되돌린다. |
long skip(long n) | 스트림에서 주어진 길이(n)만큼을 건너뛴다. |
- OutputStream의 메서드
메서드명 | 설명 |
void close() | 입력소스를 닫음으로써 사용하고 있던 자원을 반환한다. |
void flush() | 스트림의 버퍼에 있는 모든 내용을 출력소스에 쓴다. |
abstract void write(int b) | 주어진 값을 출력소스에 쓴다. |
void write(byte[] b) | 주어진 배열 b에 저장된 모든 내용을 출력소스에 쓴다. |
void write(byte[] b, int off, int len) | 주어진 배열 b에 저장된 내용 중에서 off번째부터 len개 만큼만을 읽어서 출력소스에 쓴다. |
프로그램이 종료될 때, 사용하고 닫지 않은 스트림을 JVM이 자동적으로 닫아 주기는 하지만, 스트림을 사용해서 모든 작업을 마치고 난 후에는 close를 호출해서 반드시 닫아 주어야한다. 메모리를 사용하는 스트림과 표준 입출력 스트림은 닫아 주지 않아도 된다.
2) byteArrayInputStream과 ByteArrayOutputStream
메모리, 즉 바이트배열에 데이터를 입출력 하는데 사용되는 스트림이다. 주로 다른 곳에 입출력하기 전에 데이터를 임시로 바이트배열에 담아서 변환 등의 작업을 하는데 사용된다.
3) FileInputStream과 FileOutputStream
- FileInputStream과 FileOutputstream의 생성자
생성자 | 설명 |
FileInputStream(String name) | 지정된 파일이름(name)을 가진 실제 파일과 연결된 FileInputStream을 생성. |
FileInputStream(File file) | 파일의 이름이 String이 아닌 File인스턴스로 지정해주어야 하는 점을 제외하고 FileInputStream(String name)와 같다. |
FileInputStream(FileDescriptor fdObj) | 파일 디스크립터(fdObj)로 FileInputStream을 생성한다. |
FileOutputStream(String name) | 지정된 파일이름(name)을 가진 파일과의 연결된 FileOutputStream을 생성 |
FileOutputStream(String name, boolean append) | 지정된 파일이름(name)을 가진 실제 파일과 연결된 FileOutputStream을 생성두번째 인자인 append를 true로 하면, 출력 시 기존의 파일내용의 마지막에 덧붙인다.false면, 기전의 파일내용을 덮어쓰게 된다. |
FileOutputStream(File file) | 파일의 이름을 String이 아닌 File인스턴스로 지정해주어야 하는 점을 제외하고 FileOutputStream(String name)과 같다. |
FileOutputStream(File file, boolean append) | 파일의 이름을 string이 아닌 File인스턴스로 지정해주어야 하는 점을 제외하고 FileOutputStream(String name, boolean append)과 같다. |
FileOutputStream(FileDescriptor fdObj) | 파일 디스크립터(fdObj)로 FileOutputStream을 생성한다. |
2. 바이트기반 보조스트림
1) FilterInputStream과 FilterOutputStream
FilterInputStream과 FilterOutputStream은 InputStream/OutputStream의 자손이면서 모든 보조스틀미의 조상이다.
FilterInputStream과 FilterOutputStream은 상속을 통해 원하는 작업을 수행하도록 읽고 쓰는 메서드를 오버라이딩해야 한다.
FilterInputStream 생성자는 접근 제어자가 protected이기 때문에 FilterInputStream의 인스턴스를 생성해서 사용할 수 없고 상속을 통해서 오버라이딩 되어야 한다.
//생성자
protected FilterInputStream(InputStream in)
public FilterStream(OutputStream out)
//FilterInputStream의 자손
BufferedInputStream, DataInputStream, PushbackInputStream 등
//FilterOutputStream의 자손
BufferedOutputStream, DataOutputStream, PrintStream 등
2) BufferedInputStream과 BufferedOutputStream
BufferedInputStream/BufferedOutputStream은 스트림의 입출력 효율을 높이기 위해 버퍼를 사용하는 보조스트림이다. 한 바이트씩 입출력하는 것 보다는 버퍼(바이트배열)를 이용해서 한 번에 여러 바이트를 입출력하는 것이 빠르기 때문에 대부분의 입출력 작업에 사용된다.
- BufferedInputStream의 생성자
생성자 | 설명 |
BufferedInputStream(InputStream in, int size) | 주어진 InputStream인스턴스를 입력소스(input source)로 하며 지정된 크기(byte단위)의 버퍼를 갖는 BufferedInputStream인스턴스를 생성한다. |
BufferedInputStream(InputStream in) | 주어진 InputStream인스턴스를 입력소스(input source)로 하며 버퍼의 크기를 지정해주지 않으므로 기본적으로 8192 byte 크기의 버퍼를 갖게 된다. |
- BufferedOutputStream의 생성자와 메서드
메서드/생성자 | 설명 |
BufferedOutputStream(OutputStream out, int size) | 주어진 OutputStream인스턴스를 출력소스(output source)로하며 지정된 크기(단위byte)의 버퍼를 갖는 BufferedOutputStream인스턴스를 생성. |
BufferedOutputStream(OutputStream out) | 주어진 OutputStream인스턴스를 출력소스(output source)로하며 버퍼의 크기를 지정해주지 않으므로 기본적으로 8192byte 크기의 버퍼를 갖게 됨 |
flush() | 버퍼의 모든 내용을 출력소스에 출력한 다음, 버퍼를 비운다. |
close() | flush()를 호출해서 버퍼의 모든 내용을 출력소스에 출력하고, BufferedOutputStream인스턴스가 사용하던 모든 자원을 반환한다. |
3) DataInputStream과 DataOutputStream
DataInputStream은 DataInput인테페이스를 DataOutputStream은 DataOutput인터페이스를 구현하였기 때문에, 데이터를 읽고 쓰는데 있어서 byte단위가 아닌, 8가지 기본 자료형의 단위로 읽고 쓸 수 있다는 장점이 있다.
DataOutputStream이 출력하는 형식은 각 기본 자료형 값을 16진수로 표현하여 저장한다.
- DataInputStream의 생성자 메서드(표 삽입 필요)
- DataOutputStream의 생성자와 메서드(표 삽입 필요)
문자기반 스트림 |
입출력이란?
I/O란 Input과 Outp
표준입출력과 File |
입출력이란?
I/O란 Input과 Outp
직렬화 |
입출력이란?
I/O란 Input과 Outp
'프로그래밍 > JAVA' 카테고리의 다른 글
[JAVA 이론] 네트워킹 (0) | 2022.08.15 |
---|---|
[JAVA 이론] 람다와 스트림 (0) | 2022.06.22 |
[JAVA 이론] 쓰레드 (0) | 2022.03.16 |
[JAVA 이론] Generics, Enumeration, Annotation (0) | 2022.03.13 |
[JAVA 이론] Collections Framework (0) | 2022.02.27 |