Bài 6 Lập trình với tập tin Mục tiêu Định nghĩa được tập tin là gì Phân loại được các tập tin Xử lý được tập tin văn bản Xử lý được tập tin nhị phân Xử lý được tập tin chứa cấu trúc. KTLT - Ths. Văn Thị Thiên Trang Nội dung 1 Cơ bản về tập tin 2 Thao tác với tập tin 3 Xử lý tập tin nhị phân KTLT - Ths. Văn Thị Thiên Trang 1. Cơ bản về tập tin Giới thiệu Dữ liệu nhập Chương trình Dữ liệu xuất Bàn phím Màn hình Đĩa (file) Đĩa (file) Modem Modem … Máy in KTLT - Ths. Văn Thị Thiên Trang 1. Cơ bản về tập tin Đường dẫn đến tập tin Hệ điều hành xác định 1 file bằng đường dẫn tuyệt đối hay đường dẫn tương đối. Đó là 1 chuỗi ký tự. VD về đường dẫn tuyệt đối trong C “C:\\TM1\\TM11\\f1.txt” hoặc “C:/TM1/TM11/f1.txt” Với 1 file nằm trong thư mục hiện hành, chỉ cần chỉ định file này bằng tên file ngắn gọn (đường dẫn tương đối) VD: “nhanvien.dat” KTLT - Ths. Văn Thị Thiên Trang 1. Cơ bản về tập tin Phân loại tập tin Hai dạng lưu trữ dữ liệu trong file của C Text file: Mọi dữ liệu lưu dưới dạng mã Ascii VD: Lưu trữ “AB” và số 12 cách nhau 1 khoảng trắng 010000010100001000100000 00110001 00110010 ‘A’ ‘B’ ‘‘ ‘1’ ‘2’ Binary file: Dữ liệu kí tự lưu dưới dạng mã Ascii, dữ liệu số lưu dưới dạng nhị phân của số 010000010100001000100000 0000000000001100 ‘A’ KTLT - Ths. Văn Thị Thiên Trang ‘B’ ‘‘ dạng binary của số 12 1. Cơ bản về tập tin Phân loại tập tin Hai loại file có cách lưu trữ khác nhau truy xuất dữ liệu khác nhau Binary file: dùng để lưu trữ dữ liệu dạng cấu trúc có kích thước cố định. Ghi biến cấu trúc lên file sẽ ghi 1 khối có kích thước cố định Đọc từ file ra biến cấu trúc cũng đọc từ file theo từng khối có kích thước cố định Input file: file có dữ liệu sẽ được đọc ra để đưa vào biến Output file: File sẽ chứa trị của biến khi trị của biến được ghi vào. KTLT - Ths. Văn Thị Thiên Trang Nội dung 1 Cơ bản về tập tin 2 Thao tác với tập tin 3 Xử lý tập tin nhị phân KTLT - Ths. Văn Thị Thiên Trang 2. Thao tác với tập tin Khai báo biến tập tin trong C FILE * tên_biến; VD: FILE* f; File* f; Kiểu FILE được khai báo trong thư viện <stdio.h> Biến FILE trong C là Một biến con trỏ (pointer) chỉ đến một vùng nhớ chứa thông tin về một file đã mở Thao tác tập tin Đọc dữ liệu từ tập tin ra biến Đọc file Ghi dữ liệu từ biến vào tập tin Ghi file KTLT - Ths. Văn Thị Thiên Trang 2. Thao tác với tập tin Đọc file VD: Đọc thông tin của một đồ thị được lưu trong file “C:/test.txt”. Cho biết đồ thị có hướng hay vô hướng không? 1. Mở file C:/test.txt 2. Chọn vị trí đọc: đọc từ đầu 3. Đọc số đỉnh của đồ thị ra biến n. Đọc ma trận kề của đồ thị lưu vào mảng 2 chiều G 4. Kiểm tra ma trận có đối xứng không? 5. Đóng file. KTLT - Ths. Văn Thị Thiên Trang 2. Thao tác với tập tin Các bước đọc file 1. Mở file C:/test.txt 1. Mở file để đọc 2. Chọn vị trí đọc: đọc từ đầu 2. Chọn vị trí sẽ đọc 3. Đọc số đỉnh của đồ thị ra biến n. Đọc ma trận kề của đồ thị lưu vào mảng 2 chiều G 3. Đọc data từ file biến 4. Kiểm tra ma trận có đối xứng không? 4. Xử lý biến 5. Đóng file. 5. Đóng file Chú ý: Sau khi mở file, vị trí hiện hành là đầu file Nếu đọc dữ liệu từ đầu file thì bỏ qua bước 2 Nếu viết hàm thì tên file là tham số KTLT - Ths. Văn Thị Thiên Trang 2. Thao tác với tập tin Các bước ghi file 1. Mở file để ghi 2. Chọn vị trí sẽ ghi 3. Chuẩn bị giá trị cho biến 4. Ghi giá trị của biến vào file 5. Đóng file Chú ý: Sau khi mở file, vị trí hiện hành là đầu file Nếu ghi dữ liệu từ đầu file thì bỏ qua bước 2 Nếu viết hàm thì tên file là tham số KTLT - Ths. Văn Thị Thiên Trang 2. Thao tác với tập tin Các thao tác file chuẩn Mở file Đóng file Đọc/ghi dữ liệu với file đã mở Một số thao tác khác Di chuyển trong file Kiểm tra đã hết file chưa? Thao tác với vị trí hiện hành Đổi tên/hủy 1 file đã đóng KTLT - Ths. Văn Thị Thiên Trang <stdio.h> Các thao tác file chuẩn Mở file Hàm mở file FILE * fopen (const char* filename, const char* mode); Mode: Text file Binary file Description “r”, “rt” “rb” read “w”, “wt” “wb” write, ghi đè nếu file đã tồn tại “a” “ab” append, mở để ghi thêm vào Nếu file chưa có thì tạo mới “r+”, “r+t” “rb” Mở để vừa đọc vừa ghi “w+”, “w+t” “wb” Mở để vừa đọc vừa ghi “a+”, “a+t” “ab” Mở để vừa đọc vừa ghi ở cuối file, tạo mới nếu file chưa tồn tại KTLT - Ths. Văn Thị Thiên Trang Các thao tác file chuẩn Mở file Hàm mở file FILE * fopen (const char* duong_dan, const char* mode); Trả về: NULL: thất bại !=NULL: thành công VD: FILE* f=fopen(“c:/test.txt”, “r”); KTLT - Ths. Văn Thị Thiên Trang Các thao tác file chuẩn Mở file Một tập tin sau khi mở được quản lý thông qua một con trỏ FILE. Khi mở tập tin (wb, rb), con trỏ FILE chỉ đến đầu tập tin. Khi mở tập tin (ab), con trỏ FILE chỉ đến cuối tập tin. Con trỏ FILE chỉ đến từng byte trong tập tin nhị phân Sau mỗi lần đọc tập tin, con trỏ FILE sẽ di chuyển đi một số byte bằng kích thước (byte) của khối dữ liệu đọc được. KTLT - Ths. Văn Thị Thiên Trang Các thao tác chuẩn Đóng file Đóng file int fclose(FILE* f); Ví dụ: Mở file, cho biết file đó có tồn tại không? void kiemTraFile(char* đuongdan) { FILE* f = fopen(đuongdan, “r”); if (f==NULL){ printf(“Khong mo duong file %s, duongdan); getch(); return; } printf(“File %s da duoc mo”, duongdan); fclose(f); } KTLT - Ths. Văn Thị Thiên Trang Các thao tác file chuẩn Một số thao tác khác Kiểm tra hết file chưa? Trả trị 1: hết file Trả trị 0: chưa hết file KTLT - Ths. Văn Thị Thiên Trang int feof (FILE* f); Các thao tác chuẩn Đọc ghi dữ liệu với file đã mở Thao tác với Đọc file biến Ghi biến file Ký tự char ch ch = fgetc(f); fputc(ch,f); Chuỗi ký tự char S[]; fgets(S, n, f) fputs (S,f); Số fscanf(f,”format”, &var); fprintf(f,”format”, var); n Cấu trúc nhị phân size_t fread (&bien,sizeof(struct),n,f) int fwrite (bien,sizeof(struct),n,f ) Bài tập: Tham khảo stdio.h về trị trả về của các hàm này KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi từng kí tự getc, putc, fgetc, fputc getc: đọc ký tự từ tập tin int getc ( FILE *f ); trả về ký tự đọc được hoặc trả về EOF nếu f không hợp lệ hoặc đọc đến cuối tập tin. putc: ghi ký tự ra tập tin int putc ( int Ch, FILE * f ); putc trả về EOF nếu thao tác ghi có lỗi. có thể dùng fgetc và fputc. KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi từng ký tự Ví dụ 1. Viết chương trình nhập một chuỗi tối đa 100 kí tự từ bàn phím. Lưu các ký tự là nguyên âm vào tập tin “NguyenAm.txt”. Đọc các kí tự từ tập tin này và hiển thị lên màn hình. KTLT - Ths. Văn Thị Thiên Trang Ví dụ #include <stdio.h> #include <conio.h> #include <stdlib.h> const char STRNA[] = “AEIOU”;//các nguyên âm void main() { FILE * f; //con trỏ tập tin char ch; //lưu ký tự gõ vào tư bàn phím // mở tập tin mới để ghi if ((f = fopen (“NguyenAm.txt”, “w” )) == NULL ) { printf ( “Loi mo file \n”); getch(); return; } while (( ch = getche() ) != ‘\r’ ) // đọc cho đến khi gặp ENTER if(strchr(STRNA,ch)) putc ( ch, f ); //ghi vào tập tin nguyên âm này fclose ( f ); Ví dụ //mở tập tin này ra xem if ((f = fopen (“NguyenAm.txt”, “r” )) == NULL ) { printf ( “Open file error \n”); exit (1); } printf(“Cac nguyen am la: ”); while (( ch = getc( f )) != EOF ) // đọc cho đến hết tập tin //hiển thị các kí tự này lên màn hình printf(“%c”,ch); fclose ( f ); } Đọc chuỗi kí tự từ file fgets fgets: đọc chuỗi ký tự từ tập tin. char * fgets ( char *Str, int NumOfChar, FILE *fp ); fgets đọc các ký tự trong tập tin cho đến khi gặp một trong các điều kiện: EOF gặp dòng mới đọc được (NumOfChar - 1) ký tự trước khi gặp hai điều kiện trên. fgets trả về chuỗi ký tự đọc được (kết thúc bằng \0) hoặc trả về con trỏ NULL nếu EOF hoặc có lỗi khi đọc. KTLT - Ths. Văn Thị Thiên Trang Ghi chuỗi kí tự vào file fputs fputs: ghi chuỗi ký tự ra tập tin. int fputs ( const char *Str, FILE * fp ); fputs trả về EOF nếu thao tác ghi có lỗi. KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi dữ liệu dạng bất kỳ fprintf, fscanf fprintf: int fprintf ( FILE*, định dạng, các tham biến); fscanf: int fscanf ( FILE*fp, định dạng, địa chỉ các tham biến); KTLT - Ths. Văn Thị Thiên Trang Đọc /ghi dữ liệu dạng bất kỳ Ví dụ Cho file “test.txt” có chứa: 10 1 3 2 5 8 9 11 20 59 50 Mở file, đọc dữ liệu từ file lưu vào 1 biến mảng Ghi tất cả các số nguyên tố trong mảng vào file “test. txt” (ghi thêm vào, ko xóa dãy số ban đầu) 10 1 3 2 5 8 9 11 20 59 50 Cac so nguyen to la: 3 2 5 11 59 KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi dữ liệu dạng bất kỳ Ví dụ Các hàm cần viết Đọc dữ liệu từ file ra mảng void DocFile(char duong_dan_file[], int a[], int &n); Kiểm tra một số nguyên có là nguyên tố không int KiemTraNT(int x); Ghi các số nguyên tố có trong mảng vào file void GhiFile(char duong_dan_file[], int a[], int n); Hàm main: gọi thực hiện những hàm nào? KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi dữ liệu dạng bất kỳ Ví dụ //nạp thư viện #include <stdio.h> #define MAX 100 //hàm kiểm tra số nguyên tố, trả 1: là nguyên tố ngược lại: 0 int laNguyenTo(const int &n); void main(){ //khai báo con trỏ tập tin FILE * f; //khai báo mảng arr int arr[MAX]; //mở tập tin f=fopen(“c:/dulieu.txt”, “r”); KTLT - Ths. Văn Thị Thiên Trang Đoc/ghi dữ liệu dạng bất kỳ Ví dụ //kiem tra mo thanh cong khong? if (!f) { printf(“Khong mo duoc tap tin!”); return; } //mở thành công //đọc từng số int n; n=0; while (!eof(f)){ fscanf(f, “%d”, &arr[n]); n++; }//đọc hết tập tin fclose(f); //đóng tập tin lại KTLT - Ths. Văn Thị Thiên Trang Đoc/ghi dữ liệu dạng bất kỳ Ví dụ //mở tập tin ra để viết kết quả vào f = fopen(“nguyento.txt”, “w”); //kiem tra mo thanh cong khong? if (!f) { printf(“Khong mo duoc tap tin!”); return; } //mở thành công //lặp từng phần tử mảng, kiểm tra là số nguyên tố for (int i=0; i<n; i++) if( laNguyenTo(arr[i])) //viết số nguyên tố vào tập tin fprintf(f, “%4d”, arr[i]); fclose(f); //đóng tập tin lại } //kết thúc hàm main KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi dữ liệu dạng bất kỳ Ví dụ //hàm kiểm tra số nguyên tố, trả 1: là nguyên tố ngược lại: 0 int laNguyenTo(const int &n){ if (n<2) return 0; int tam=sqrt(n); for(int i=2;i<=t;i++) if (n%i==0) return 0; //không là số nguyên tố return 1; } KTLT - Ths. Văn Thị Thiên Trang //là số nguyên tố Nội dung 1 Cơ bản về tập tin 2 Thao tác với tập tin 3 Xử lý tập tin nhị phân KTLT - Ths. Văn Thị Thiên Trang 3. Đọc/ghi tập tin nhị phần fread, fwrite fread() : đọc fread(&ptr, Item_size, num_Item, FILE*) fread đọc NumItem khối dữ liệu, mỗi khối có kích thước ItemSize từ fp và chứa vào vùng nhớ xác định bởi Ptr fread trả về số khối dữ liệu đọc được Nếu có lỗi hoặc EOF thì giá trị trả về nhỏ hơn NumItem fwrite() : ghi fwrite(ptr, Item_size, num_Item, FILE*); fwrite ghi khối (NumItem x ItemSize) xác dịnh bởi Ptr ra fp. KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi tập tin nhị phân Ví dụ File nhị phân thường được dùng để lư trữ cấu trúc có kích thước cố định. Ví dụ: struct HS { char Name[31]; int d; } Kích thước của cấu trúc: 33 bytes. HS h, a[10]; int n; fread(&h, sizeof(HS), 1, f); Fread(a, sizeof(HS), n, f); Một đơn vị đọc ghi file là 1 cấu trúc. KTLT - Ths. Văn Thị Thiên Trang Đọc/ghi tập tin nhị phân Ví dụ Viết chương trình nhập vào một danh sách tối đa 30 sinh viên thông tin gồm: tên, năm sinh, điểm trung bình. Lưu các sinh viên này vào tập tin “sinhvien.dat” Đọc dữ liệu từ tập tin này, hiển thị lên màn hình thông tin của những sinh viên có điểm trung bình > =5.0 KTLT - Ths. Văn Thị Thiên Trang Tóm lại Đọc/ghi kí tự Đọc/ghi dữ liệu định dạng bất kỳ Đọc/ghi cấu trúc KTLT - Ths. Văn Thị Thiên Trang KTLT - Ths. Văn Thị Thiên Trang