자바 I/O 개론

Kim taegwan·2026년 3월 31일

I/O 는 Input / Output 의 약자입니다. 프로그램이 외부와 데이터를 주고받는 모든 행위를 I/O 라고 합니다.

System.out.println("Hello");         // Output : 프로그램 → 콘솔 화면
Scanner sc = new Scanner(System.in); // Input  : 키보드 → 프로그램

이렇게 우리는 매일 쓰고 있었다.

스트림(Stream) 이란?

Untitled

I/O 를 이해하려면 스트림(Stream) 을 먼저 이해해야 합니다. 스트림은 직역하면 "흐름" 입니다.

스트림의 핵심 2가지

1. 단방향성 — 스트림은 한 방향으로만 흐릅니다

입력 스트림 (InputStream, Reader) : 외부 → 프로그램 (읽기 전용)
출력 스트림 (OutputStream, Writer) : 프로그램 → 외부 (쓰기 전용)

그래서 파일을 읽으면서 동시에 쓰려면 스트림이 2개 필요합니다.

[파일] ──► InputStream ──► [프로그램] ← 읽기용
[파일] ◄── OutputStream ◄── [프로그램] ← 쓰기용

2. 순차적 접근 — 앞에서부터 순서대로 처리합니다

마치 편의점 계산대처럼, 먼저 온 데이터가 먼저 처리됩니다. (FIFO 구조) 한 번 지나간 데이터는 다시 꺼낼 수 없습니다.


딱 2가지 기준으로 나뉩니다

기준 1 : 방향 → 읽기냐? 쓰기냐?

읽기  →  InputStream  또는  Reader
쓰기  →  OutputStream 또는  Writer

기준 2 : 데이터 종류 → 이미지/동영상이냐? 텍스트냐?

이미지, 동영상, zip 등  →  바이트 기반  (InputStream / OutputStream)
텍스트, 한글 등         →  문자 기반   (Reader / Writer)

전체 구조 한눈에 보기

java.io 패키지
│
├──  바이트 기반  (모든 종류의 파일)
│     InputStream  ──► FileInputStream, BufferedInputStream
│     OutputStream ──► FileOutputStream, BufferedOutputStream
│
└── 문자 기반  (텍스트 파일 전용, 한글 안깨짐)
      Reader  ──► FileReader, BufferedReader, InputStreamReader
      Writer  ──► FileWriter, BufferedWriter, OutputStreamWriter

클래스 이름을 보면 역할이 보입니다.

FileInputStream  =  File(파일) + Input(읽기) + Stream(바이트)
                 =  "파일에서 바이트로 읽기"
                 
FileOutputStream =  File(파일) + Out(쓰기) + Stream(바이트)
                 =  "파일에서 바이트로 쓰기"

BufferedWriter   =  Buffered(버퍼) + Writer(문자 쓰기)
                 =  "버퍼를 사용해서 문자로 쓰기"

이름 규칙만 알면 처음 보는 클래스도 역할이 보입니다!


왜 바이트와 문자로 나뉘나요?

바이트 스트림만 쓰면 안 되나요?

한글 '가' 를 바이트로 표현하면?
→ UTF-8 기준으로 3바이트  [0xEA, 0xB0, 0x80]

바이트 스트림으로 1바이트씩 읽으면?
→ '가' 가 세 조각으로 잘려서 읽힘
→ 화면에 깨진 글자 출력

문자 스트림을 쓰면?

문자 스트림은 '가' 가 몇 바이트인지 스스로 알고 있음
→ 3바이트를 통째로 읽어서 '가' 로 변환
→ 정상 출력 

즉, 문자 스트림은 한글 자동 처리 전문가입니다.

스트림 체이닝 — 기능을 조립하는 방법

스트림은 여러 개를 연결(체이닝) 해서 기능을 확장할 수 있습니다.

마치 USB 허브처럼, 기본 스트림에 기능을 하나씩 붙이는 방식입니다.

// FileReader (파일 읽기) + BufferedReader (성능 향상 + 한 줄 읽기) 연결
BufferedReader br = new BufferedReader(new FileReader("example.txt"));
[파일] → FileReader → BufferedReader → [프로그램]
          (문자 읽기)   (버퍼 + readLine 기능 추가)
             ↑ 기반 스트림      ↑ 보조 스트림

기반 스트림에 보조 스트림을 감싸서 기능을 추가합니다.

언제 어떤 클래스를 써야 하나요?

강의가 끝나면 이 기준 하나로 선택할 수 있게 됩니다.

 텍스트 파일 (한글 포함 가능)
    읽기 → FileReader         성능 필요하면 → BufferedReader
    쓰기 → FileWriter         성능 필요하면 → BufferedWriter

이미지 / 동영상 / zip (바이너리 파일)
    읽기 → FileInputStream    성능 필요하면 → BufferedInputStream
    쓰기 → FileOutputStream   성능 필요하면 → BufferedOutputStream

키보드 입력
    간단할 때       → Scanner
    입력이 많을 때  → BufferedReader + InputStreamReader

핵심 요약

구분입력 (읽기)출력 (쓰기)
바이트 기반InputStreamOutputStream
문자 기반ReaderWriter

기억할 것 딱 3가지

1. 스트림 = 단방향 데이터 흐름
2. 바이트 기반  vs  문자 기반 (한글이면 문자 기반!)
3. 클래스 이름에 역할이 담겨 있다

0개의 댓글