oop> java -cp bin FileCopy
복사할 원본파일명을 입력하세요 : D:\a.txt
붙여넣기할 파일명을 입력하세요: D:\acopy.txt
<<byte단위로 읽고 쓰기>>
원본파일이 없는 경우 "복사할 원본파일이 없습니다" 메세지 출력된다
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Scanner;
public class FileCopy {
public static void main(String[] args) {
Scanner sc =new Scanner(System.in);
System.out.print("원본파일명:");
String originFileName = sc.nextLine();
System.out.print("복제본파일명:");
String copyFileName = sc.nextLine();
FileInputStream fis = null;
FileOutputStream fos = null;
try {
fis = new FileInputStream(originFileName);
} catch (FileNotFoundException e) {
System.out.println("원본파일이 없습니다");
// e.printStackTrace();
return;
}
try {
fos = new FileOutputStream(copyFileName);
} catch (FileNotFoundException e) {
//E드라이브 없는데 E드라이브에 만들라하면 이러한 exception
e.printStackTrace();
return;
}
/*
int readValue;
try {
while((readValue = fis.read()) != -1) {
// 끝을 만나면 -1을 반환한다. 마우스 올리면 설명
fos.write(readValue);
}
} catch (IOException e) {
e.printStackTrace();
*/
int readCnt; // 읽어온 바이트수
byte[] bArr= new byte[1024];
try {
while((readCnt = fis.read(bArr)) != -1) {
// fos.write(bArr); // 이거는 틀림.
//다시 돌릴때마다 읽어온 바이트수마다 써야해서
fos.write(bArr, 0, readCnt);
// 배열의 0번 인덱스부터, 1kb씩 읽어서 1kb씩 쓰기
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
fis.close();
} catch (IOException e) {
e.printStackTrace();
}
try {
fos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
※ Java의 파일 출력 스트림에서 사용되는 메서드로, 지정된 바이트 배열의 특정 위치에서부터 지정된 길이만큼 바이트를 파일로 출력하는 역할을 합니다. 이때 "offset"은 시작 위치를 나타냅니다.
b: 출력할 바이트 배열
off: 시작 위치 (offset), 바이트 배열에서 어디서부터 데이터를 읽을지를 나타냅니다.
len: 출력할 바이트 수
이 메서드를 호출하면, 지정된 바이트 배열(b)에서 off 위치부터 시작하여 len만큼의 바이트를 파일 출력 스트림에 쓰게 됩니다. 즉, 바이트 배열 내에서 off부터 off + len - 1 위치까지의 바이트 데이터가 파일로 출력됩니다.
byte[] data = {65, 66, 67, 68, 69}; // ASCII values for A, B, C, D, E
fos.write(data, 1, 3);
위 코드는 data 배열의 1번째 위치에서 시작하여 3개의 바이트를 파일 출력 스트림에 쓰게 됩니다. 따라서 파일에는 'B', 'C', 'D' 바이트가 순서대로 저장될 것입니다.
※ 파일 복사 예제 2
파일 복사의 원리는 FileInputStream에서 읽은 바이트를 바로 FileOutputStream으로 출력하는 것.
임의의 JPEG 그림 파일을 하나 준비해 파일 이름을 test.jpg로 변경한 다음 C:/Temp 폴더에 저장한다.
package ch18.sec03.exam03;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
public class CopyExample {
public static void main(String[] args) throws Exception {
String originalFileName = "C:/Temp/test.jpg";
String targetFileName = "C:/Temp/test2.jpg";
// 입출력 스트림 생성
InputStream is = new FileInputStream(originalFileName);
OutputStream os = new FileOutputStream(targetFileName);
// 읽은 바이트를 저장할 배열 생성
byte[] data = new byte[1024];
while(true) {
int num = is.read(data); // 최대 1024바이트를 읽고 배열에 저장, 읽은 바이트는 리턴
if(num == -1) break; // 파일을 다 읽으면 while문 종료
os.write(data, 0, num); // 읽은 바이트 수만큼 출력
}
os.flush(); // 내부 버퍼 잔류 바이트를 출력하고 버퍼를 비움
os.close();
is.close();
System.out.println("복사가 잘 되었습니다.");
}
}
Java 9부터 좀 더 편리하게 입력 스트림에서 출력 스트림으로 바이트를 복사하는 transferTo() 메소드가
InputStream에 추가되었다. 위 코드에서 아래 라인은 다음과 같이 한줄로 대체가 가능하다.
// 16~21 라인
byte[] data = new byte[1024];
while(true) {
int num = is.read(data);
if(num == -1) break;
os.write(data, 0, num);
}
// 대체
is.transferTo(os);
'언어 > Java' 카테고리의 다른 글
필터스트림, 객체직렬화 (0) | 2023.08.09 |
---|---|
메타클래스, File 정보 가져오기 (0) | 2023.08.09 |
입출력 스트림 예시 (0) | 2023.08.09 |
프린트 스트림, System.in 예시 (0) | 2023.08.09 |
입출력 스트림(Stream) (0) | 2023.08.09 |