파일 접근 모드
파일 모드 한정자
파일 접근 모드와 같이 작성해서 사용한다
ex. rb, wt, …
파일 접근 모드, 파일 모드 한정자 예시 with. fwrite()
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
enum { LENGTH = 5 };
int main(void)
{
int data[LENGTH] = { 11, 22, 33, 44, 55 };
size_t count;
FILE* out = fopen("output.txt", "wb");
count = fwrite(data, sizeof(data[0]), LENGTH, out);
// fwrite() 함수는 binary file을 적을 때 쓰는 함수
// out에 LENGTH개 sizeof(data[0])만큼씩 data로부터 읽어서 작성
// 결국 LENGTH == count
fclose(out);
out = NULL;
return 0;
}
파일 위치 표시자(File Position Indicator)
파일 스트림 안에서 현재 위치를 나타내주는 표시자이다
파일 스트림에는 총 3가지 표시자가 있다
1. EOF 표시자: 읽다가 EOF를 만났을 때 set 되는 표시자
2. ERROR 표시자: 읽다가 에러 났을 때 set 되는 표시자, 다시 reset하려면 clearerr() 함수 호출
3. 파일 위치 표시자: 현재 읽고 있는 위치 표시자
파일 위치 표시자 예시 with. rewind()
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#define LENGTH (1024)
int main(void)
{
char filename[] = "output.txt";
FILE* stream;
int data[LENGTH];
size_t i, num_read;
stream = fopen(filename, "rb");
if (!stream)
{
perror("error while opening");
return 1;
}
num_read = fread(data, sizeof(data[0]), LENGTH, stream);
/* fread() 함수는 binary file을 읽을 때 쓰는 함수. */
/* stream으로부터 최대 LENGTH개 sizeof(data[0])만큼씩 읽어서, data에 저장해라. */
/* num_read는 읽은 데이터의 개수. */
printf("%zu\n", num_read);
for (i = 0; i < num_read; ++i)
{
printf("%d ", data[i]);
}
rewind(stream);
printf("\nrewind() has been called.\n");
num_read = fread(data, sizeof(data[0]), LENGTH, stream);
printf("%zu\n", num_read);
for (i = 0; i < num_read; ++i)
{
printf("%d ", data[i]);
}
if (fclose(stream) != 0)
{
perror("error while closing");
return 2;
}
return 0;
}
int fseek(FILE* stream, long offset, int origin)
파일 위치 표시자를 origin으로부터 offset만큼 이동한다
성공시 0을 반환하고
실패시 0이 아닌수를 반환한
origin 매개변수로는 아래의 3가지 종류가 있다
fseek() 예시
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#define LENGTH (1024)
int main(void)
{
char filename[] = "output.txt";
FILE* stream;
int data[LENGTH];
size_t i, num_read;
stream = fopen(filename, "rb");
if (!stream)
{
perror("error while opening");
return 1;
}
num_read = fread(data, sizeof(data[0]), LENGTH, stream);
for (i = 0; i < num_read; ++i)
{
printf("%d ", data[i]);
}
fseek(stream, 1 * sizeof(data[0]), SEEK_SET);
printf("\nfseek() has been called.\n");
num_read = fread(data, sizeof(data[0]), LENGTH, stream);
for (i = 0; i < num_read; ++i)
{
printf("%d ", data[i]);
}
if (fclose(stream) != 0)
{
perror("error while closing");
return 2;
}
return 0;
}
long ftell(FILE* stream)
파일 위치 표시자의 현재 위치를 알려주는 함수이다
실패시 -1을 반환한다
일반적인 파일 스트림에선 실패가 발생하진 않는다
파일 크기가 없는 파일 스트림(ex. 소켓, 파이프, ...)과
파일 크기가 제공되지 않는 경우(ex. 가상 파일 시스템, ...)에 발생한다
파일 모드 한정자에 따른 ftell() 동작
binary:
파일의 시작 지점으로부터 몇 바이트 떨어져 있는지 알려준다
text:
어떤 값을 반환할지 모른다 (unspecified behavior)
하지만 유효한 값이기때문에,
fseek() 함수의 offset 매개변수의 인자로 전달해서 사용하는 것은 가능하다
ftell() 예시
// hello.txt 안의 내용
Hello, :world!:
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#define TRUE (1)
#define FALSE (0)
void print_with_repeats(const char* filename);
int main(void)
{
print_with_repeats("hello.txt");
return 0;
}
void print_with_repeats(const char* filename)
{
long pos = -1L;
int repeating = FALSE;
int c;
FILE* file;
file = fopen(filename, "r");
if (NULL == file) {
perror("error while opening");
return;
}
c = fgetc(file);
while (c != EOF)
{
if (c != ':')
{
putchar(c);
goto next_char;
}
if (FALSE == repeating)
{
if (pos < 0)
{
/* start mark */
pos = ftell(file);
if (pos < 0) {
perror("error while getting start position");
break;
}
} else {
/* end mark */
repeating = TRUE;
if (fseek(file, pos, SEEK_SET) != 0) {
perror("error while fseek() to start position");
break;
}
}
goto next_char;
}
/* revisited end mark */
repeating = FALSE;
pos = -1L;
next_char:
c = fgetc(file);
}
if (fclose(file) != 0) {
perror("error while closing");
return;
}
return;
}
'C > [코드조선] C 핵심' 카테고리의 다른 글
[C] 전처리기 지시자와 컴파일 플래그 (0) | 2024.02.17 |
---|---|
[C] 입출력 리디렉션, 커맨드 라인 인자 (0) | 2024.02.17 |
[C] 파일 입출력 (1) (0) | 2024.02.16 |
[C] 열거형과 공용체 (0) | 2024.02.15 |
[C] 구조체 vs. 클래스 (0) | 2024.02.14 |