1. 자바에서의 입출력
- 컴퓨터 내부 또는 외부의 장치와 프로그램간의 데이터를 주고 받는 것을 말한다.
스트림
- 데이터를 운반하는데 사용되는 연결통로
- 단방향 통신만 가능하기 때문에 하나의 스트림으로 입력과 출력을 동시에 처리할 수 없다.

보조 스트림
- 스트림의 기능을 보완하기 위한 보조 스트림이 제공된다.
- 보조 스트림만으로는 입출력을 처리할 수 없고, 스트림을 먼저 생성한 다음에 이를 이용해서 보조 스트림을 생성해야 한다.
FileInputStream fis = new FileInputStream("test.txt");
BufferedInputStream bis = new BufferedInputStream(fis);
bis.read();

문자 기반 스트림(Reader, Writer)
- Java에서는 char가 2byte이기 때문에 바이트 기반의 스트림으로 문자를 처리하는데 어려움이 있다.
- 문자 데이터를 입출력할 때는 바이트기반 스트림 대신 문자기반 스트림을 사용하자.
- 보조 스트림 역시 이름만 다를 뿐 사용 목적과 방식은 바이트기반과 다르지 않다.
2. 표준 입출력과 File
표준 입출력(System.in, System.out, System.err)
- System.in
- System.out
- System.err
표준 입출력 대상 변경(setOut(), setErr(), setIn())
- 입출력을 콘솔 이외에 다른 입출력 대상으로 변경하는 것이 가능하다.
RandomAccessFile
- 하나의 클래스로 파일의 입력과 출력을 모두 할 수 있도록 되어 있다.
- 파일의 어느 위치에나 읽기/쓰기가 가능하다.
File
- File 클래스를 통해서 파일과 디렉토리를 다룰 수 있다.
3. 직렬화(Serialization)
- 객체를 데이터 스트림으로 만드는 것
- 스트림으로부터 데이터를 읽어서 객체를 만드는 것을 역직렬화라고 한다.
Serializable
- Serializable 인터페이스를 구현한 클래스는 직렬화가 가능하다.
- 조상 클래스가 Serializable을 구현했다면 해당 클래스는 직렬화가 가능하다.
- 조상 클래스가 Serializable을 구현하지 않았다면 자손 클래스를 직렬화할 때 조상 클래스에 정의된 인스턴스 변수는 직렬화 대상에서 제외된다.
- 따라서, 모든 클래스의 조상인 Object는 Serializable을 구현하지 않았기 때문에 직렬화할 수 없다.
transient
- 직렬화하고자 하는 객체의 클래스에 직렬화가 안되는 객체에 대한 참조를 포함하고 있다면, 제어자 transient를 붙여서 직렬화 대상에서 제외할 수 있다.
직렬화 가능한 클래스의 버전관리
- 직렬화된 객체를 역직렬화할 떄 직렬화 했을 때와 같은 클래스를 사용해야 한다.
- 객체가 직렬화될 때 클래스에 정의된 멤버들의 정보를 이용해서 serialVersionUID라는 클래스의 버전을 자동생성해서 직렬화 내용에 포함한다.
- 클래스 버전을 수동으로 관리할 수 있다.
- 클래스 내에 serialVersionUID를 정의해두면, 클래스의 내용이 바뀌어도 클래스의 버전이 자동생성된 값으로 변경되지 않는다.
- serialVersionUID의 값은 어떠한 값으로도 지정할 수 있지만 중복되지 않기 위해 serialVer.exe를 사용해서 생성된 값을 사용하는 것이 일반적이다.