읽기
파일을 읽기 위해서는 다음 순서로 코드를 작성해야 합니다.
파일 객체 생성: -
File file = new File("filename.txt");파일 입력 스트림 생성: -
FileInputStream inputStream = new FileInputStream(file);버퍼 생성: -
byte[] buffer = new byte[1024];입력 스트림으로부터 데이터를 버퍼에 읽어옴: -
inputStream.read(buffer);버퍼에서 읽어온 데이터를 문자열로 변환: -
String data = new String(buffer);입력 스트림 닫기: -
inputStream.close();
1. Byte 단위로 읽기
InputStream은 Byte 단위로 읽어 들이는 것으로 InputStream 확장해서 만든 FileInputStream 클래스를 사용하여 파일에서 데이터를 읽게 합니다.
FileInputStream fileInputStream = null;
try {
fileInputStream = new FileInputStream(fileName) ;
int readChar = 0;
while ((readChar = fileInputStream.read()) != -1) {
System.out.println((char)readChar);
}
} catch (IOException e) {
System.out.println("파일을 확인해 주세요");
throw new RuntimeException(e);
} finally {
if (fileInputStream != null ) {
try {
fileInputStream.close();
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}3 line : 파일 객체 생성 합니다.
FileInputStream 생성자의 인수로 파일을 넘겨주면 내부에서 File를 객체를 생성합니다.
파일 읽기의 1, 2번 사항 입니다.
4 line : read() 메서드는 Data를 한 Byte씩 읽어서 값이 없으면 -1로 돌려 주는 메서드로 파일을 읽어 마지막 인지 체크하기 위해 선언한 변수로 초기값 0으로 설정합니다.
5 line : Data를 한 Byte씩 읽어서 없으면 while문을 벗어납니다.
6 line : 읽은 문자는 Char로 변환 해서 출력합니다.
8 - 11 line : File에 관한 예외 처리 로직
12 - 17 line : File을 열어서 작업을 했으므로 열려 있는 파일을 닫아야 합니다.
2-1-1. 예제 1의 문제점
한글 파일인 경우 한글이 깨지는 문제 입니다. 해당 문제를 해결하기 위해서는 문자셋을 지정해야 하므로 InputStreamReader 클래스를 사용하여 FileInputStream객체에서 읽어들인 데이터를 문자셋을 변환합니다.
3 line : InputStreamReader 메서드 시그니처로의 두번째 파라메터에 문자셋을 지정 하여 읽어야 합니다.
파일의 문자셋에 맞는 문자셋를 지정 합니다. ( "UTF-8", "EUC-KR" )
2. Line 단위로 읽기
line 단위로 읽기 위해서는 reader 객체나 자바 8 이상에서는 Files 클래스를 이용하는 방법이 있습니다.
2-1. InputStream / Reader 클래스 사용
Reader 클래스를 상속 받은 BufferedReader를 Byte로 읽어 들이는 InputStream 클래스와 같이 사용해서 Line 단위로 읽게할 수 있습니다.
3 - 6 line : Byte 단위로 읽어 들이는 FileInputStream 클래스에 InputStreamReader 클래스를 이용하여 문자셋으로 적용하고 읽어 들인 것을 BufferReader를 사용하여 Line단위로 읽을수 있게 합니다.
7 - 9 line : bufferedReader.readLine()은 읽을 데이터가 없으면 null로 반환하고 있으면 라인의 데이터를 돌려 주는 메서드여서 readLine 변수를 사용하고 데이터가 없으면 while문을 탈출 합니다.
3. Line 단위로 읽기 문자셋 변경
3-1. InputStream / Reader 클래스 사용
2-2. Line 단위로 읽기 코드에서 라인 단위로 읽은 데이터를 getBytes() 메서드를 사용해서 문자셋 변경을 하고 문자열로 바꾸면 됩니다.
2 line : getBytes를 사용해서 문자셋 변환("UTF-8", "EUC-KR") 합니다.
3 line : System.out으로 출력하기 위해 문자열로 변환합니다.
3-2. FileReader / BufferedReader 클래스 사용
InputStream 클래스를 FileReader 클래스로 변경을 하면 됩니다. FileReader 샹성자로 두번째 파라메터가 Charset 타입을 전달 해야하며 내부적으로는 FileInputStream를 사용합니다. 다음은 FileReader 클래스생성자 입니다.
FileReader / BufferedReader 클래스 사용 소스
3 - 4 line : InputStream 클래스 대신 FileReader 클래스로 변경하고 Charset.forName() 메서드를 사용하여 Charset 타입으로 변경합니다.
나머지는 2-2-1과 동일 합니다.
4. CSV 파일 읽기
CSV 파일은 쉼표(",")로 구분된 파일로 라인 단위로 읽고 쉼표(",") 하면 쉽게 만들수 있습니다.
CSV 파일을 관련 부분은 다음과 같습니다.
6- 11 line : 해더 포함 이면 결과에 해더 정보를 추가하고 해더 미포함 이면 해더 포함으로 설정을 변경합니다. 그래야 14 line 에서 읽은 데이터를 6 line조건이 만족하여 결과에 데이터가 포함됩니다.
19 - 28 line : 구분자가 있는 경우 구분자를 기준으로 21 line 에서 구분자로 잘라서 배열에 넣어서 반환 하고 구분자가 없는 경우 파라터로 받은 ( row ) 데이터를 그냥 반환 합니다.
주의 사항 : 성능 및 트랜잭션애 대한 고려를 해야 합니다.
업무처리를 여기서 하는 경우 : 성능, DB 처리 갯수는 여러 사항에 대해서 고려 하여 동기적, 비동기적으로 설계 할지 결정을 해아합니다.
호출한 곳에서 하는 경우 : 성능, DB 처리 갯수등 여러 사항에 대해서 고려 해야 히지만 병렬, 분산 등을 선택의 폭이 넓을 것으로 생각이 됩니다. 업무처리를 여기서 하는 경우에서 병렬, 분산까지 고려 해서 코드를 작성하기는 난이도가 더 높습니다.
전체 소스는 다음과 같으며 소스에 대한 설명을 주석에 표시 하였습니다.
4-1. 구분자 "," 인 EUC-KR로 된 파일을 UTF-8로 변환
공통 유틸을 사용의 read() 메서드 호출시 해더포함, 구분자(","), EUC-KR을 UTF-8로 변경 하기 위한 소스 코트 입니다.


Last updated