Java

2024.05.14 Java 유용한 클래스 파일 입력 스트림(바이트 기반)

정훈5 2024. 5. 14. 10:21

 

 

 

 

a. txt 만들기

더보기
package io.file.ch01;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;

public class MyFileInputStream {

	public static void main(String[] args) {

		// 외부에 있는 a.txt 파일 데이터를 읽으려면 input 이 필요하다.
		FileInputStream in = null;

		try {
			in = new FileInputStream("a.txt");

			// 1단계
			// int readData = in.read(); // 오류 뜨면 2번째꺼 선택

			// 2단계
//			System.out.println( (char)in.read());
//			System.out.println( (char)in.read());
//			System.out.println( (char)in.read());
			
			// 3단계
			// 읽을 데이터가 더 이상 없다면 -1을 반환 한다.
			int readData;
			while( ( readData = in.read() ) != -1 ) {
				System.out.print( (char)readData );
			}
			
			// 4단계 FileInputStream (기반 스트림) 대상에 접근해서 한 바이트씩 읽어 들이는 기능을 가진다.
			// 1byte ->  -128 +127 범위  : a --> 97, A --> 65, 대 (정수값 얼마야?) -->? 

		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}

	}

}

 

기반 스트림 (Base Stream)이란 뭘까?

기반 스트림데이터 소스와 직접 연결되는 스트림으로, 실제 데이터 읽기나 쓰기 작업을 수행합니다.
이 스트림들은 데이터의 실제 입력 소스(파일, 메모리, 네트워크 연결 등)에 직접 연결되어 데이터를 바이트 단위로 읽거나 쓰는 기본적인 기능을 제공합니다.

 

바이트 기반 스트림

FileInputStream, FileOutputStream, socketInputStream, socketOutputStream 등이 있으며,
이들은 바이트 데이터를 처리합니다.

 

문자 기반 스트림

 FileReader, FileWriter등이 있으며, 이들은 문자 데이터를 처리합니다.

 

기반 스트림 (Base Stream)이란 뭘까?

기반 스트림은 데이터 소스와 직접 연결되는 스트림으로, 실제 데이터 읽기나 쓰기 작업을 수행합니다.
이 스트림들은 데이터의 실제 입력 소스(파일, 메모리, 네트워크 연결 등)에 직접 연결되어 데이터를 바이트 단위로 읽거나 쓰는 기본적인 기능을 제공합니다.

 

바이트 기반 스트림
FileInputStream, FileOutputStream, SocketInputStream, SocketOutputStream 등이 있으며,
이들은 바이트 데이터를 처리합니다.

 

문자 기반 스트림
FileReader, FileWriter 등이 있으며, 이들은 문자 데이터를 처리합니다.

 


보조 스트림 (Filter Stream)이란?

보조 스트림은 기반 스트림 또는 다른 보조 스트림에 연결되어 사용됩니다.
이 스트림들은 데이터를 변환하거나, 추가 기능을 제공하거나, 성능을 향상시키는 역할을 합니다.
보조 스트림은 자체적으로 데이터 소스에 연결되지 않으며, 항상 다른 스트림을 필요로 합니다.

 

  • 버퍼링
    BufferedInputStream, BufferedOutputStream, BufferedReader, BufferedWriter는 내부적으로 버퍼를 사용하여 데이터를 모아서 한 번에 처리합니다. 이는 입출력 효율을 대폭 향상시킵니다.

  • 데이터 변환
    DataInputStream, **DataOutputStream**은 기본 데이터 타입(int, float, long 등)을 쉽게 읽고 쓸 수 있게 해 줍니다.

  • 객체 직렬화
    ObjectInputStream, ObjectOutputStream은 객체를 바이트 스트림으로 직렬화하거나 바이트 스트림에서
    객체를 복원하는 기능을 제공합니다.

  • 문자 인코딩
    InputStreamReader, OutputStreamWriter는 바이트 스트림을 문자 스트림으로 변환하거나
    반대의 작업을 할 때 사용되며, 인코딩 변환을 처리합니다.

기반 스트림과 보조 스트림에 활용

FileInputStream fis = new FileInputStream("input.txt"); // 기반 스트림
BufferedInputStream bis = new BufferedInputStream(fis); // 보조 스트림

 

데코레이터로 장식

 

 

기반 스트림 + 보조스트림을 사용해 보자.

더보기
package io.file.ch01;

import java.io.BufferedInputStream;
import java.io.FileInputStream;
import java.io.IOException;

public class MyBufferedInputStream {

	public static void main(String[] args) {

		// 보조 스트림에 사용 -> 기반 스트림이 필요하다.
		FileInputStream fin = null;
		BufferedInputStream bfin = null;

		try {
			// 기반 스트림
			fin = new FileInputStream("a.txt");

			// 보조 스트림(기반스트림)
			bfin = new BufferedInputStream(fin);

			int data;

			while ((data = bfin.read()) != -1) {
				System.out.print((char) data);
			}

		} catch (Exception e) {
			// 리소스 자원 정리 -> 반대로 -> 열었던 자원에 순서를 반대로 닫아 주면 된다.
			if (bfin != null) {
				try {
					bfin.close();
				} catch (IOException e1) {
					e1.printStackTrace();
				} // end of try-catch
			} // end of if()
			
			if (fin != null) {
				try {
					fin.close();
				} catch (IOException e1) {
					e1.printStackTrace();
				} // end of try- catch
			} // end of if()

		}

	} // end of main

} // end of class
Hello World.
By Tenco.
한글작성

 

작동 방식

  1. 첫 번째 read() 호출
    BufferedInputStream은 내부 버퍼를 사용하여 데이터 소스로부터 많은 양의 데이터를 미리 읽습니다
    (예를 들어, 버퍼 크기가 8192바이트일 경우 최대 8192바이트를 읽음).

  2. 데이터 반환
    사용자가 read()를 호출할 때마다, BufferedInputStream은 버퍼에서 한 바이트씩 데이터를 반환합니다.

  3. 버퍼 재충전
    버퍼에 있는 모든 데이터가 읽혔다면, 다음 read() 호출 때 다시 데이터 소스에서 버퍼 크기만큼 데이터를 읽어
    버퍼를 재충전합니다.

 

BufferedInputStream.read()를 호출하여 한 바이트씩 데이터를 읽습니다.
이 때, 실제 파일 접근은 버퍼가 비워질 때만 발생하므로 파일 접근 횟수가 줄어들어 성능이 향상됩니다.