70.2 서식을 지정하여 파일에서 문자열 읽기
이제 앞에서 생성한 hello.txt 파일의 내용을 읽어보겠습니다. 파일을 읽을 때도 fopen 함수로 파일을 열어서 파일 포인터를 얻은 뒤 fscanf 함수로 서식을 지정하여 파일의 내용을 읽습니다(stdio.h 헤더 파일에 선언되어 있습니다).
-
fscanf(파일포인터, 서식, 변수의주소1, 변수의주소2, …);
- int fscanf(FILE * const _Stream, char const * const _Format, ...);
- 성공하면 읽어온 값의 개수를 반환, 실패하면 EOF(-1)를 반환
다음 내용을 소스 코드 편집 창에 입력한 뒤 Ctrl+F5 키를 눌러서 실행해보세요.
file_read_format.c
#define _CRT_SECURE_NO_WARNINGS // fopen 보안 경고로 인한 컴파일 에러 방지 #include <stdio.h> // fopen, fscanf, fclose 함수가 선언된 헤더 파일 int main() { char s1[10]; int num1; FILE *fp = fopen("hello.txt", "r"); // hello.txt 파일을 읽기 모드(r)로 열기. // 파일 포인터를 반환 fscanf(fp, "%s %d", s1, &num1); // 서식을 지정하여 파일에서 문자열 읽기 printf("%s %d\n", s1, num1); // Hello 100: 파일에서 읽은 값을 출력 fclose(fp); // 파일 포인터 닫기 return 0; }
실행 결과
Hello 100
먼저 fopen 함수를 사용하여 hello.txt 파일을 읽기 모드(r)로 엽니다.
FILE *fp = fopen("hello.txt", "r"); // hello.txt 파일을 읽기 모드(r)로 열기. // 파일 포인터를 반환
fscanf 함수는 파일 포인터를 넣는다는 점 말고는 scanf 함수와 사용법이 같습니다. 즉, 파일에서 문자열을 읽은 뒤 서식에 맞추어서 값을 변수에 저장합니다. 여기서는 서식을 "%s %d"로 지정했으므로 "Hello" 부분은 문자 배열 s1에 저장되고, 100 부분은 정수형 변수 num1에 저장됩니다.
fscanf(fp, "%s %d", s1, &num1); // 서식을 지정하여 파일에서 문자열 읽기
printf로 s1과 num1의 값을 출력해보면 "Hello"와 100이 나옵니다.
printf("%s %d\n", s1, num1); // Hello 100: 파일에서 읽은 값을 출력
마찬가지로 파일 읽기 작업이 끝났다면 fclose 함수로 파일 포인터를 닫아줍니다.
fclose(fp); // 파일 포인터 닫기
서식을 지정하여 파일에서 문자열을 읽는 과정을 그림으로 나타내면 다음과 같습니다.
![](https://dojang.io/pluginfile.php/672/mod_page/content/23/unit70-2.png)
fprintf 함수는 stdout 매크로를 활용해서 화면에 문자열을 출력했는데 fscanf도 비슷한 사용 방법이 있지 않을까요? fscanf 함수는 stdin 매크로를 활용하면 사용자가 입력한 값을 변수에 저장할 수 있습니다.
char s1[10]; int num1; fscanf(stdin, "%s %d", s1, &num1); // 서식을 지정하여 표준 입력(stdin)에서 문자열 읽기
즉, fscanf(stdin, ...);은 scanf 함수와 동작이 같습니다.
fprintf, fscanf 등의 함수의 매개변수에서 파일 포인터 부분을 보면 FILE* const _Stream와 같이 스트림(stream)이라고 되어 있습니다. 보통 파일 포인터를 파일 스트림이라고도 하는데 스트림은 물 등의 액체가 흐르는 것을 뜻합니다. 파이프 속에 물이 계속 흘러다니는 것처럼 파일 스트림도 파일의 데이터를 연속적으로 처리한다고 해서 스트림입니다.
즉, 파일에서 데이터를 처리할 때마다 매번 파일을 여는 것이 아니라 파일 스트림을 한 번 생성해서 계속 데이터를 쓰거나 가져오는 방식이죠. 여기서 fopen으로 파일을 읽기 전용으로 열면 입력 스트림, 쓰기 전용으로 열면 출력 스트림, 읽기/쓰기로 열면 입출력 스트림입니다. 파일 모드에 따라 단방향, 양방향이 되죠. 마찬가지로 stdin은 입력 스트림, stdout, stderr는 출력 스트림입니다.