14 차시 파일 (2) 강 C 프로그래밍 10
메모리 메모리 주메모리 : 속도가빠르다. 가격이비싸다. 휘발성. 프로그램실행에필수 보조메모리 : 속도가느리다. 가격이싸다. 영구적. 영구적인자료보관, 대용량의데이터는보조메모리이용 파일 이름 + 확장자, 날짜, 크기 폴더 강 C 프로그래밍 11
프로그램이파일을지원하면 1 프로그램실행의연속성 2 번거로운데이터입력자동화 실행종료실행 실행 실행 실행 Program Program Program Program Program 변수의내용을파일로저장 파일에서읽어변수의값을복원 시간 데이터읽기 데이터읽기 데이터읽기 3 데이터의분할처리 4 데이터의이동 Computer A Computer B Program Program Program 1 2 3 데이터파일 데이터파일 이동 데이터파일 프로그램이한층강력해진다. 강 C 프로그래밍 12
C 언어의파일 파일의종류 텍스트파일 : 문자로구성된파일. 문자열을저장한것 확장자가.txt,.log,.ini,.xml 로구성된다. 문서편집기, 메모장을통하여내용을쉽게확인할수있다. 이진 (binary) 파일 : 각종숫자를포함한이진데이터를저장한것 ( 포괄적 ) mp3, jpg, avi,.exe 를비롯한대부분의파일 A Dream Within A Dream by Edgar Allan Poe EmailPrint Take this kiss upon the brow! And, in parting from you now, Thus much let me avow-- You are not wrong, who deem That my days have been a dream; Yet if hope has flown away 텍스트파일 이진파일강C프로그래밍 13
C 언어에서파일생성과기록 파일열기 파일이름과목적 ( 읽기또는쓰기 ) 지정 파일의스트림지시자 ( 핸들 ) 를얻는다. 파일읽기 / 쓰기 용도에맞도록파일의내용을읽어메모리로가져오거나, 메모리의내용을파일에기록한다. 파일닫기 파일작업이완료되면파일을마무리한다. 파일을닫으면새로열기전까지파일접근을할수없다. 강 C 프로그래밍 14
파일의이름 파일이름 저장될데이터의특성을잘나타낼수있는이름을선택 문자열이므로, 사이에기록한다. 알파벳, 숫자, 일부기호사용가능. 대소문자구별없음. \, /, *, *,?,, <, >, 는사용불가 ( 운영체제마다약간다를수있다 ) 폴더 폴더와폴더, 폴더와파일이름사이에 \ 또는 / 을붙여야한다 ( 운영체제지시사항. 리눅스의경우 / 만가능 ) 안에 \ 를쓸때에는 \\ 처럼두개를써야한다 ( 이스케이프시퀀스 ). 강 C 프로그래밍 15
읽기쓰기모드 파일을열때모드를지정해야한다. 보통읽기또는쓰기중하나를지정한다. 두가지를모두하더라도, 읽기를모두한후, 쓰기를한다. 두가지일을섞어서하면관리가어렵고성능도저하된다. 읽기를하려면파일이존재해야한다. 쓰기를하려면파일존재가무관하다. 강 C 프로그래밍 16
파일과운영체제 파일관리는운영체제의역할이다 ( 메모리처럼 ). FILE 구조체는파일접근을위한정보구조체이다. 프로그램 운영체제 FILE *fp; 개발자 FILE 구조체 ( 스트림기본정보 ) 시스템 스트림 보조기억장치 (HDD) 파일 1 파일 2 강 C 프로그래밍 17
표준입출력 stdin, stdout, stderr 도 FILE * 이다. 사전에정의된입출력스트림구조체의포인터이다. 준비되어있으므로입출력에바로사용가능하다. 프로그램 운영체제 printf, scanf 표준입력 FILE 구조체 표준출력 FILE 구조체 표준입력스트림 표준출력스트림 키보드 모니터 FILE *stdin FILE *stdout 강 C 프로그래밍 18
파일열기 FILE *fopen(const char *filename, const char *mode) filename : 열고자하는파일이름 mode : 파일열기모드 반환값 : 지정한파일의 FILE 구조체포인터 ( 스트림지시자 ) 예 FILE *pfile = fopen( hporter.txt, r ); FILE *pfile = fopen( score.dat, wb ); FILE *pfile = fopen( data\\report.txt, w ); FILE *pfile = fopen( diary.txt, r+ ); 강 C 프로그래밍 19
파일열기 모드 기본추가 예 ) r, rt, wb 반환값 모드의미 r 읽기 ( 파일이반드시존재 ) w 쓰기 ( 파일을새로생성. 기존파일있으면내용삭제 ) a 기존파일에추가하기 ( 마지막이후에쓰기 ) 추가 b, t 이진파일또는텍스트파일 ( t 는생략가능 ) 추가 + 업데이트가능. 기본동작에추가로업데이트를한다. 추가 x w 와결합하여, 기존파일이있으면열기실패 (C11) FILE 구조체포인터 강 C 프로그래밍 20
파일열기 여러파일을사용할때 하나의 FILE 구조체포인터를이용 FILE *pfile; pfile = fopen( 1번파일, r ); fclose(pfile); // 1번파일사용종료 pfile = fopen( 2번파일, wb ); 동시에여러개의파일을이용한다면여러개의 FILE 구조체포인터를이용 FILE *pfile1, *pfile2, *pfile3; pfile1 = fopen( 1번파일, r ); pfile2 = fopen( 2번파일, wb ); pfile3 = fopen( 3번파일, w ); 강 C 프로그래밍 21
파일입출력 ( 텍스트모드 ) int fprintf(file * stream, const char * format,... ); int fscanf (FILE * stream, const char * format,... ); char *fgets(char * str, int num, FILE * stream ); int fputs(const char * str, FILE * stream ); int fgetc (FILE * stream ); int fputc (int character, FILE * stream ); 강 C 프로그래밍 22
문자입출력 int fgetc(file *stream) int fputc(int character, FILE *stream) 하나의문자읽기 / 쓰기 읽기 / 쓰기에성공한크기반환 ( 보통 1) 실패할수있다. 강 C 프로그래밍 23
문자입출력 #include <stdio.h> #include <stdio.h> int main ( ) { FILE * pfile; char c; int main ( ) { FILE * pfile; int c; } pfile = fopen ("alphabet.txt,"w"); if (pfile!= NULL) { for (c = 'A' ; c <= 'Z' ; c++) fputc ( c, pfile ); fclose (pfile); } return 0; pfile = fopen ("alphabet.txt","r"); if (pfile == NULL) perror(" 파일열기실패 "); else { do { c = fgetc(pfile); // 파일에서한문자가져와 if (c!= EOF) // 제대로가져왔으면 putc(c, stdin );// 화면에출력 } while (c!= EOF); // 파일의끝까지반복 fclose (pfile); } // end of if return 0; } // end of main 강 C 프로그래밍 24
문자열입출력 char * fgets ( char * str, int num, FILE * stream ); int fputs ( const char * str, FILE * stream ); 행단위문자입출력 최대 num-1 바이트를읽는다. 마지막 1 바이트는 \0 pfile = fopen ("sentence.txt", "r"); if (pfile == NULL) perror (" 파일열기실패 "); else { if(fgets(mystr, 100, pfile)!= NULL) // 파일가져오기에성공하면 puts (mystr); // 화면에출력 fclose (pfile); } 강 C 프로그래밍 25
문자열입출력 ( 형식지정 ) int fprintf (FILE *stream, const char * format,...); int fscanf (FILE *stream, const char * format,...); printf, scanf와같은형식으로사용한다. fscanf(pfile, %d %d, &i, &j); sscanf, sprintf 를이용하여메모리에작업한후, 파일에기록하는방법도있다. 결과물에별도가공이가능하다. fgets(str, sizeof(str), pfile); sscanf(str, %d %d, &i, &j); 강 C 프로그래밍 26
파일입출력 ( 바이너리모드 ) 파일열기, 닫기는텍스트파일과같다 ( 모드만다르다 ). 이진파일은텍스트파일과다르다. int fread(void *buf, int size, int n, FILE *fp); int fwrite(const void *buf, int size, int n, FILE *fp); buf : 읽기 / 쓰기를데이터공간 size : 한블록의크기 n : 블록의개수 반환값 : 읽기 / 쓰기에성공한블록수 강 C 프로그래밍 27
이진파일읽기 / 쓰기 메모리 buf 메모리 buf size 바이트 #1 #2 #n size * n 바이트 size * n 바이트 파일 파일 #1 #2 #n size 바이트 fread fwrite 강 C 프로그래밍 28
이진파일읽기 / 쓰기 int fread(void *buf, int size, int n, FILE *fp); size 크기의블록을 n개만큼이진파일을읽어 buf에저장하라. ( size * n 바이트 ) 다음의세가지는동일하다. fread(buf, 10, 100, fp); fread(buf, 100, 10, fp); fread(buf, 1000, 1, fp); 반환값은작업한크기 ( 블록수 ) int fwrite(const void *buf, int size, int n, FILE *fp); 반환값은작업한크기 ( 블록개수 ) size 와다르면쓰기에러 강 C 프로그래밍 29
파일닫기 int fclose(file *fp); 정상실행이면 0, 문제가있으면 EOF 반환 닫기를꼭해야하나 강 C 프로그래밍 30
미니과제 프로그램을처음실행하면관리자의생일 ( 년월일 ) 을묻는다. 그다음프로그램을실행할때부터는관리자의생일을물어정확하게알면 GOOD이라고출력하고틀리면다시묻는프로그램을작성하라. C:\> birth.exe 관리자의생일을입력하시면기억하겠습니다. 1997 5 12 관리자의생일이저장되었습니다. 1997년 5월 12일. C:\> birth.exe 관리자를확인합니다. 생일을입력하세요. 1998 3 3 관리자가아닙니다. 실행할수없습니다. C:\> birth.exe 관리자를확인합니다. 생일을입력하세요. 1997 5 12 관리자님안녕하세요. 강 C 프로그래밍 31
파일위치조정 파일은순차접근메모리 파일은앞에서뒤로차례로기록되어있다. 읽기위치를조정할수있고, 앞부분을건너뛰고뒷부분을읽을수있다. int fseek (FILE *fp, long offset, int mode); offset과 mode로지정한위치로읽는위치를이동한다. mode는 SEEK_SET( 파일의시작부터 ), SEEK_CUR( 현재위치 ), SEEK_END( 파일의끝 ) 중하나. 읽은부분 읽은부분 0 EOF 파일위치지시자 0 EOF fseek( ) 강 C 프로그래밍 32
파일위치조정 FILE * pfile; pfile = fopen ( text.txt", "wb"); // 텍스트파일이지만, 이진모드로기록했다. fputs ( Hello World.", pfile); // 일단문자열을기록한다. fseek (pfile, 6, SEEK_SET); // 기록위치를조정한다. fputs ( Cprog", pfile ); // 문자열을추가기록한다. fclose ( pfile ); 0 1 2 3 4 5 6 H e l l o W o r l d. fseek text.txt 파일에 Hello Cprog. 가들어있다. 좋은방법은아니다. 불가피할때에만쓴다. 강 C 프로그래밍 33
파일위치조정 void rewind( FILE *fp ) 읽는위치를처음으로되돌린다. 읽기쓰기겸용모드 (+) 에서모드전환시이용한다 ( 읽기후쓰기전환 ) int fflush( FILE *fp ) 성능향상을위해버퍼링을하는데, 버퍼의내용을디스크에강제반영한다. 비정상종료에대비한다. long ftell( FILE *fp ) 읽는위치를반환한다. 강 C 프로그래밍 34
버퍼링 CPU 기다림성능저하 보조기억장치 빠른장치 느린장치 기다림없음 CPU 버퍼 일괄처리 보조기억장치 빠른장치 빠른공간 느린장치 주의할점은? 강 C 프로그래밍 35
파일의끝, EOF int feof ( FILE * stream ); 파일의끝이면 True를, 파일의끝이아니면 False를반환 FILE * pfile; int size = 0; pfile = fopen ( document.txt","r"); if (pfile==null) perror ("Error opening file"); else { while (fgetc(pfile)!= EOF) { ++size; } if (feof(pfile)) { printf(" 파일크기는 %d 바이트 \n", size); } 또는 while (!feof(pfile) ) { fgetc(pfile); ++size; } printf(" 파일크기는 %d 바이트 \n", size); } } fclose (pfile); 강 C 프로그래밍 36
파일운용 int rename (const char *oldname, const char *newname); // 파일이름변경 int remove (const char *filename); // 파일삭제 주의할점 파일삭제로남을괴롭히지말자. 강 C 프로그래밍 37
그외 휴지통이란 그외의파일관련기능 폴더생성, 삭제 파일목록 강 C 프로그래밍 38
실습문제 파일의이름을입력하면파일의크기를표시하는프로그램을 작성하라. 키보드를통하여입력한문장을파일로저장하는프로그램을 작성하라. Ctrl-Z 를누르면입력이종료되고파일에저장한 다. 강 C 프로그래밍 39