=============================================================================
=============================================================================
涉及到的知识点有:
六、stat函数
七、fread 和 fwrite函数
八、fopen的a模式说明
九、fopen的b模式说明
十、sftp传输文件时的说明
十一、fopen的其他模式简要说明
十二、实现二进制文件的拷贝
十三、fseek函数
十四、ftell函数
十五、fflush函数
十六、remove函数 和 rename函数 (文件删除函数和文件改名函数)
十七、通过fwrite将结构体保存到二进制文件中
课堂练习
=============================================================================
=============================================================================
六、stat函数
需要包含头文件有:
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
功能:得到文件的各种属性(包括文件的属性、文件的建立时间、文件的大小等信息)。和文件的内容并没有关系。
int stat(const char *pathname, struct stat *buf);
函数的第一个参数:代表文件名。
函数的第二个参数:是struct stat结构。
一般头文件在"cd /usr/include"下面,这里是标准C程序头文件,如果你的头文件前加了 <sys/*>,那说明这是系统调用函数头文件,其在"cd /usr/include/sys"下面。
函数都是获取文件(普通文件、目录、管道、socket、字符、块)的属性。函数原型#include <sys/stat.h>。
--------------------------------------
linux下示例代码如下:
1 #include <stdio.h> 2 #include <sys/types.h> 3 #include <sys/stat.h> 4 #include <unistd.h> 5 6 int main() 7 { 8 struct stat st = { 0 }; //该结构在头文件#include <sys/stat.h>里面已经定义过了,只需要去使用它就行了。 9 stat("a.txt", &st); //调用完stat函数后,st里面就得到了该文件的属性。 10 11 int size = st.st_size; //得到文件的大小。单位是:字节。 12 printf("%d ", size); //78 13 14 return 0; 15 }
文件对应的属性: struct stat { mode_t st_mode; //文件对应的模式,文件,目录等。 ino_t st_ino; //inode节点号。 dev_t st_dev; //设备号码。 dev_t st_rdev; //特殊设备号码。 nlink_t st_nlink; //文件的连接数。 uid_t st_uid; //文件所有者。 gid_t st_gid; //文件所有者对应的组。 off_t st_size; //普通文件,对应的文件字节数。 time_t st_atime; //文件最后被访问的时间。 time_t st_mtime; //文件内容最后被修改的时间。 time_t st_ctime; //文件状态改变时间。 blksize_t st_blksize; //文件内容对应的块大小。 blkcnt_t st_blocks; //伟建内容对应的块数量。 };
=============================================================================
七、fread 和 fwrite函数
文本文件:就是我们能看的懂的文件。
二进制文件:就是我们看不懂的文件。
之前学的:fgets、fputs、fprintf、fscanf这些函数都是针对文本文件读写的,不能对一个二进制文件进行读写。
除了文本文件之外的文件都是二进制文件,比如图像、视频、音乐、可执行程序这些都是二进制的。
(其实文本文件也是二进制文件,文本文件是一种特殊的二进制文件,文本文件里面都是ASCII码。)
之前学习的内容都是往文件里面写一个字符串。
如果要把一个int整数直接写入文件,这个文件就不是文本文件了。
--------------------------------------
#include <stdio.h>
size_t fread(void *ptr, size_t size, size_t nmemb, FILE *stream);
size_t fwrite(const void *ptr, size_t size, size_t nmemb, FILE *stream);
第一个参数是buf的内存地址;
第二个参数是每个单位的大小;
第三个参数是写多少个单位;
第四个参数是fopen返回的文件指针。
返回值:返回的是实际写入的数据块数目。
fread的返回值是成功读取到的单位个数。
fread第二个参数代表了一个单位多大,第三个参数代表一次要读多少个单位。
功能:这两个函数以二进制形式对文件进行操作,不局限于文本文件。
--------------------------------------
linux下示例代码如下:
1 #include <stdio.h> 2 3 int main01() 4 { 5 FILE *p = fopen("a.dat", "w"); 6 7 int a = 100; 8 fwrite(&a, 1, sizeof(int), p); //要往文件里面写4个字节的内容。 9 //fwrite(&a, sizeof(int), 1, p); //二者等价。 10 a = 123456789; //再往文件里面写4个字节的内容。 11 fwrite(&a, 1, sizeof(int), p); 12 13 fclose(p); 14 15 return 0; 16 } 17 18 int main() 19 { 20 FILE *p = fopen("a.dat", "r"); 21 22 while (1) 23 { 24 //int a = 0; //以int的方式打开。 25 //fread(&a, 1, sizeof(int), p); 26 unsigned char a = 0; //以每个字节的方式打开。 27 fread(&a, 1, sizeof(char), p); 28 if (feof(p)) 29 break; 30 //printf("%d ", a); 31 printf("%x ", a); //以16进制的方式显示,小端对齐。 32 } 33 fclose(p); 34 35 return 0; 36 } 37 输出结果为: 38 64 39 0 40 0 41 0 42 15 43 cd 44 5b 45 7
-----------------------------------------------------------------------------
通过fread读取文件的每个字节。
linux下示例代码如下:
int main(int argc, char **args) { if (argc < 2) return 0; FILE *p = fopen(args[1], "r"); while (1) { //int a = 0; //以int的方式打开。 //fread(&a, 1, sizeof(int), p); unsigned char a = 0; //以每个字节的方式打开。 fread(&a, 1, sizeof(char), p); if (feof(p)) break; //printf("%d ", a); printf("%x ", a); //小端对齐。 } fclose(p); return 0; }
=============================================================================
八、fopen的a模式说明
FILE *fopen(const char *path, const char *mode);
a 以附加的方式打开只写文件。若文件不存在,则会建立该文件。
如果文件存在,写入的数据会被加到文件尾,即文件原先的内容会被保留。(EOF符保留)
a+ 以附加的方式打开可读写文件。若文件不存在,则会建立该文件。
如果文件存在,写入的数据会被加到文件尾,即文件原先的内容会被保留。(原来的EOF符不保留)
即:a的作用是:如果文件不存在,那么a和w是一样的;如果文件存在,那么不覆盖这个文件,而是往文件后面追加内容。
=============================================================================
九、fopen的b模式说明
r 以只读方式打开文件,该文件必须存在,且文件必须是可读的。
r+ 以可读写方式打开文件,该文件必须存在。
rb+ 读写打开一个二进制文件,允许读写数据,文件必须存在。
注意:b模式也只能在windows下去演示,在linux、unix和Android下无效。
windows所有的文本文件的每一行都是以
结尾的,而不是以
结尾的。
(即windows系统下的文本文件以
来进行换行的。)
在windows下,如果读文件的时候,只加"r"参数,那么系统会自动把
前面的
吃掉,而一旦添加了参数b,那么系统就不会自动吃掉
前面的
了。
在windows下,如果写文件的时候,只加"w"参数,那么系统会自动在
前面添加一个
,而一旦添加了b参数,那么系统就不会自动在
前面动添加
了。
linux下所有的文本文件,每一行本来就是以 结尾的,前面没有 ,参数b在linux下是无效的。
小规律:
在windows读写是一个二进制文件的时候,一般要加b,防止系统添加无谓的
。
但如果读写的是一个文本文件,那么不要加b,这样可以不用单独处理这个
了。
小结:
所以windows的文本文件要比linux的文本文件要大一些,因为windows的每一行会比linux的每一行多一个
(即多1个字节)。
并没有为什么,这是当年微软在设计的时候,是从DOS过来的,那个时候DOS就是这样的。
所以有时候,把linux的文本文件拿到windows下打开的情况下,会发现不换行了。
即:windows和linux(unix)的文本文件是不一样的。
=============================================================================
十、sftp传输文件时的说明
如果是要用sftp去下载一个文本文件的时候:操作如下:
sftp> ascii
Using ascii mode to transfer files.
sftp> get file11.c
Downloading file11.c from /home/chen/001/01/文件操作day01/file11.c
100% 779 bytes 779 bytes/s 00:00:00
/home/chen/001/01/文件操作day01/file11.c: 779 bytes transferred in 0 seconds (779 bytes/s)
sftp>
--------------------------------------
如果是要用sftp去下载一个二进制文件的时候:操作如下:
sftp> binary
Using binary mode to transfer files.
sftp> get file11.c
Downloading file11.c from /home/chen/001/01/文件操作day01/file11.c
100% 779 bytes 779 bytes/s 00:00:00
/home/chen/001/01/文件操作day01/file11.c: 779 bytes transferred in 0 seconds (779 bytes/s)
sftp>
如下图所示:
=============================================================================
十一、fopen的其他模式简要说明
=============================================================================
十二、实现二进制文件的拷贝
windows下示例代码:
1 #include <stdio.h> 2 #include <sys/stat.h> 3 #include <stdlib.h> 4 5 #define NUM 1024 * 64 //设置文件大小阈值为64K。 6 7 int main(int argc, char **args) 8 { 9 if (argc < 3) 10 return 0; 11 12 FILE *p = fopen(args[1], "rb"); 13 if (p == NULL) 14 return 0; 15 16 FILE *p1 = fopen(args[2], "wb"); 17 if (p1 == NULL) 18 return 0; 19 20 //先得到文件的大小。 21 struct stat st = { 0 }; 22 stat(args[1], &st); 23 int size = st.st_size; 24 25 //判断阈值。 26 if (size >= NUM) 27 size = NUM; 28 29 //再根据文件的大小,动态分配一个堆内存出来。 30 char *buf = malloc(size); 31 32 while(!feof(p)) 33 { 34 //char a = 0; 35 //fread(&a, 1, 1, p); //一次读一个char。 36 //char a[1024] = { 0 }; //一次读一个1024个字节。 37 //fread(a, 1, sizeof(a), p); 38 //fwrite(a, 1, 1, p1); //一次写一个char。 39 //fwrite(a, 1, sizeof(a), p1); //一次写一个1024个字节。 40 41 int res = fread(buf, 1, size, p); //把读的返回值传给要写的参数里面。 42 fwrite(buf, 1, res, p1); 43 } 44 fclose(p); 45 fclose(p1); 46 free(buf); 47 48 return 0; 49 }
=============================================================================
十三、fseek函数
int fseek(FILE *stream, long offset, int whence);
函数功能:设置文件指针stream的位置。
如果执行成功,stream将指向以whence为基准,偏移offset(指针偏移量)个字节的位置,函数返回0。
如果执行失败,则不改变stream指向的位置,函数返回一个非0值。
第一个参数:stream为文件指针。
第二个参数:offset为偏移量,整数表示正向偏移,负数表示负向偏移。
第三个参数:whence为设定文件从哪里开始偏移,可能取值为:SEEK_SET、SEEK_CUR或SEEK_END。
SEEK_SET:文件开头。
SEEK_CUR:当前位置。
SEEK_END:文件结尾。
例如:fseek(fp, 3, SEEK_SET);
实验得出:
往前偏移超出文件末尾位置,还是返回0;
往回偏移超出文件首位置,还是返回0。
所以需要小心使用。
其实FILE结构内部是有一个指针的,每次调用文件读写函数时,这些函数就会自动移动这个指针。
默认情况下该指针只能从前往后移动。
windows下示例代码:
1 #include <stdio.h> 2 3 int main01() 4 { 5 FILE *p = fopen("a.dat", "w"); 6 7 char a[10] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; 8 fwrite(a, 1, sizeof(a), p); 9 fclose(p); 10 11 return 0; 12 } 13 14 int main() 15 { 16 FILE *p = fopen("a.dat", "r"); 17 18 fseek(p, 2, SEEK_SET); //将文件指针从文件开始处位移2个字节。 19 20 int i; 21 for (i =0; i < 2; i++) 22 { 23 //char a = 0; 24 //fread(&a, 1, sizeof(a), p); 25 26 char a[2] = { 0 }; 27 fread(a, 1, sizeof(a), p); 28 29 //fseek(p, -2, SEEK_CUR); //将指针从当前位置回去2个字节。 30 //fseek(p, 0, SEEK_SET); //将指针指向文件开始。 31 fseek(p, 0, SEEK_END); //将指针指向文件结尾。 32 printf("%d, %d ", a[0], a[1]); 33 } 34 fclose(p); 35 36 return 0; 37 } 38 输出结果为: 39 2, 3 40 0, 0
windows下示例代码:
1 #include <stdio.h> 2 3 //慢速生成超大文件的方法。 4 int main01() 5 { 6 FILE *p = fopen("a.dat", "w"); 7 8 int i; 9 for (i = 0; i < 10000000; i++) 10 { 11 char a = 0; 12 fwrite(&a, 1, sizeof(a), p); 13 } 14 fclose(p); 15 16 return 0; 17 } 18 19 //利用fseek函数瞬间生成超大文件的方法。 20 int main() 21 { 22 FILE *p = fopen("a.dat", "w"); 23 24 fseek(p, 10000000, SEEK_SET); //将文件指针从文件开始处位移10000000个字节。 25 26 char a = 0; 27 fwrite(&a, 1, sizeof(a), p); 28 fclose(p); 29 30 return 0; 31 }
=============================================================================
十四、ftell函数
ftell函数用于得到文件位置指针当前位置相对于文件首的偏移字节。
但是在随机方式存取文件时,由于文件位置频繁的前后移动,程序不容易确定文件的当前位置。
long ftell(FILE *stream);
例如:long len = ftell(fp);
可以通过fseek和ftell得到文件大小:
fseek(fp, 0, SEEK_END);
long len = ftell(fp);
--------------------------------------
windows下示例代码:
1 #include <stdio.h> 2 3 int main(int argc, char **args) 4 { 5 if (argc < 2) 6 return 0; 7 8 FILE *p = fopen(args[1], "r"); 9 if (p == NULL) 10 return 0; 11 12 fseek(p, 0, SEEK_END); 13 long size = ftell(p); 14 printf("%ld ", size); 15 fclose(p); 16 17 return 0; 18 }
=============================================================================
十五、fflush函数
文本的读可以用:fgets和fscanf。
文本的写可以用:fputs和fprintf。
二进制文件读可以用:fread。
二进制文件写可以用:fwrite。
其实c语言所有的文件操作函数都是缓冲区函数。 即都是针对缓冲区进行操作的。
文件读写缓冲区的说明如下图所示:
--------------------------------------
那么我们现在想绕过缓冲区,想直接将缓冲区的内容写入文件中(即磁盘)。该如何办呢?答:使用fflush函数。
fflush函数可以将缓冲区中任何未写入的数据直接写入文件(即磁盘)中。
函数执行成功则返回0,失败则返回EOF。
int fflush(FILE *stream);
由于fflush是实时的将缓冲区的内容写入磁盘,所以不要大量的去使用该函数;(因为会使程序执行效率降低,而且会影响磁盘寿命。)
但如果是特别敏感的数据,可以通过fflush写入磁盘(比如密码),防止由于电脑的各种故障,内存数据的丢失。
(因为内存一断电就没有数据了,而磁盘断电数据还在,不会丢失。)
--------------------------------------
windows下示例代码:
1 //在缓冲区里面的代码: 2 #include <stdio.h> 3 4 int main() 5 { 6 FILE *p = fopen("a.txt", "w"); 7 8 while (1) 9 { 10 char a[100] = { 0 }; 11 scanf("%s", a); 12 if (strcmp(a, "exit") == 0) 13 break; 14 fprintf(p, "%s ", a); 15 } 16 fclose(p); 17 return 0; 18 } 19 -------------------------------------- 20 //绕过缓冲区里面的代码: 21 #include <stdio.h> 22 23 int main() 24 { 25 FILE *p = fopen("a.txt", "w"); 26 27 while (1) 28 { 29 char a[100] = { 0 }; 30 scanf("%s", a); 31 if (strcmp(a, "exit") == 0) 32 break; 33 fprintf(p, "%s ", a); 34 fflush(p); //把缓冲区的数据直接同步到磁盘。 35 } 36 fclose(p); 37 return 0; 38 }
=============================================================================
十六、remove函数 和 rename函数 (文件删除函数和文件改名函数)
remove函数删除指定的文件。
int remove(const char *pathname);
参数pathname为指定要删除的文件名,如果是windows下文件名与路径可以用反斜杠分隔,也可以用斜杠/分隔。
rename函数将指定的文件改名。
int rename(const char *OldFilename, const char *NewFilename);
=============================================================================
十七、通过fwrite将结构体保存到二进制文件中
linux下示例代码:
1 #include <stdio.h> 2 #include <string.h> 3 4 struct man 5 { 6 char name[20]; 7 int age; 8 }; 9 //向文件中写一个结构体。 10 int insert() 11 { 12 //struct man m = {"苍老师", 40}; 13 //struct man m[3] = { {"苍老师", 40}, {"饭岛老师", 30}, {"陈冠希", 50} }; 14 struct man m = { 0 }; 15 16 FILE *p = fopen("a.dat", "a"); //a 以附加的方式打开只写文件。若文件不存在,则会建立该文件。 17 //如果文件存在,写入的数据会被加到文件尾,即文件原先的内容会被保留。(EOF符保留) 18 if (p == NULL) 19 return 0; 20 //fwrite(&m, 1, sizeof(struct man), p); 21 //fwrite(m, 3, sizeof(struct man), p); 22 23 while (1) 24 { 25 printf("请输入名字:"); 26 scanf("%s", m.name); 27 if (strcmp(m.name, "exit") == 0) 28 break; 29 printf("请输入年龄:"); 30 scanf("%d", &m.age); 31 fwrite(&m, 1, sizeof(struct man), p); 32 } 33 fclose(p); 34 return 0; 35 } 36 //向文件中读一个结构体。 37 int select() 38 { 39 //struct man m = { 0 }; 40 //struct man m[3] = { 0 }; 41 struct man m = { 0 }; 42 43 FILE *p = fopen("a.dat", "r"); 44 if (p ==NULL) 45 return 0; 46 //fread(&m, 1, sizeof(struct man), p); 47 //fread(m, 3, sizeof(struct man), p); 48 49 while (1) 50 { 51 fread(&m, 1, sizeof(struct man), p); 52 if (feof(p)) 53 break; 54 printf("%s, %d ", m.name, m.age); 55 } 56 /* 57 int i; 58 for (i = 0; i < 3; i++) 59 { 60 //printf("%s, %d ", m.name, m.age); 61 printf("%s, %d ", m[i].name, m[i].age); 62 } 63 */ 64 fclose(p); 65 return 0; 66 } 67 //参数1代表写入,参数2代表读出。 68 int main(int argc, int **args) 69 { 70 if (argc < 2) 71 return 0; 72 char c = args[1][0]; 73 if (c == '1') 74 insert(); 75 if (c == '2') 76 select(); 77 return 0; 78 }
=============================================================================
课堂练习:
上面的代码功能是:只能添加姓名和年龄,显示的时候只能全部显示出来。
需要显示的时候,如果输入all,就全部显示,如果具体输入某一个人的名字,那么只显示这个人的名字和年龄。
如果输入一个不存在的人名,那么就显示not found。
linux下示例代码:
1 #include <stdio.h> 2 #include <string.h> 3 4 struct man 5 { 6 char name[20]; 7 int age; 8 }; 9 //向文件中写一个结构体。 10 int myinsert() 11 { 12 //struct man m = {"苍老师", 40}; 13 //struct man m[3] = { {"苍老师", 40}, {"饭岛老师", 30}, {"陈冠希", 50} }; 14 struct man m = { 0 }; 15 16 FILE *p = fopen("a.dat", "a"); //a 以附加的方式打开只写文件。若文件不存在,则会建立该文件。 17 //如果文件存在,写入的数据会被加到文件尾,即文件原先的内容会被保留。(EOF符保留) 18 if (p == NULL) 19 return 0; 20 //fwrite(&m, 1, sizeof(struct man), p); 21 //fwrite(m, 3, sizeof(struct man), p); 22 23 while (1) 24 { 25 printf("请输入名字:"); 26 scanf("%s", m.name); 27 if (strcmp(m.name, "exit") == 0) 28 break; 29 printf("请输入年龄:"); 30 scanf("%d", &m.age); 31 fwrite(&m, 1, sizeof(struct man), p); 32 } 33 fclose(p); 34 return 0; 35 } 36 //向文件中读一个结构体。 37 int myselect() 38 { 39 //struct man m = { 0 }; 40 //struct man m[3] = { 0 }; 41 struct man m = { 0 }; 42 43 char name[30] = { 0 }; 44 printf("请输入名字:"); 45 scanf("%s", name); 46 47 FILE *p = fopen("a.dat", "r"); 48 if (p ==NULL) 49 return 0; 50 //fread(&m, 1, sizeof(struct man), p); 51 //fread(m, 3, sizeof(struct man), p); 52 53 int status = 0; 54 while (1) 55 { 56 fread(&m, 1, sizeof(struct man), p); 57 if (feof(p)) 58 break; 59 60 if (strcmp(name, "all") == 0) 61 { 62 printf("%s, %d ", m.name, m.age); 63 status = 1; 64 } 65 else 66 { 67 if (strcmp(name, m.name) == 0) 68 { 69 printf("%s, %d ", m.name, m.age); 70 status = 1; 71 } 72 } 73 } 74 /* 75 int i; 76 for (i = 0; i < 3; i++) 77 { 78 //printf("%s, %d ", m.name, m.age); 79 printf("%s, %d ", m[i].name, m[i].age); 80 } 81 */ 82 fclose(p); 83 if (status == 0) 84 printf("没有找到! "); 85 return 0; 86 } 87 //参数1代表写入,参数2代表读出。 88 int main(int argc, int **args) 89 { 90 if (argc < 2) 91 return 0; 92 char c = args[1][0]; 93 if (c == '1') 94 myinsert(); 95 if (c == '2') 96 myselect(); 97 return 0; 98 }
=============================================================================
继续课堂练习:
可以删除一个指定的人名和对应的年龄,如果输入一个没有的名字,那么什么也不做,不能增加新的文件。
linux下示例代码:
1 #include <stdio.h> 2 #include <string.h> 3 #include <stdlib.h> 4 5 struct man 6 { 7 char name[20]; 8 int age; 9 }; 10 //向文件中写一个结构体。 11 int myinsert() 12 { 13 //struct man m = {"苍老师", 40}; 14 //struct man m[3] = { {"苍老师", 40}, {"饭岛老师", 30}, {"陈冠希", 50} }; 15 struct man m = { 0 }; 16 17 FILE *p = fopen("a.dat", "a"); //a 以附加的方式打开只写文件。若文件不存在,则会建立该文件。 18 //如果文件存在,写入的数据会被加到文件尾,即文件原先的内容会被保留。(EOF符保留) 19 if (p == NULL) 20 return 0; 21 22 //fwrite(&m, 1, sizeof(struct man), p); 23 //fwrite(m, 3, sizeof(struct man), p); 24 25 while (1) 26 { 27 printf("请输入名字:"); 28 scanf("%s", m.name); 29 if (strcmp(m.name, "exit") == 0) 30 break; 31 printf("请输入年龄:"); 32 scanf("%d", &m.age); 33 fwrite(&m, 1, sizeof(struct man), p); 34 } 35 fclose(p); 36 return 0; 37 } 38 //向文件中读一个结构体。 39 int myselect() 40 { 41 //struct man m = { 0 }; 42 //struct man m[3] = { 0 }; 43 struct man m = { 0 }; 44 45 char name[30] = { 0 }; 46 printf("请输入名字:"); 47 scanf("%s", name); 48 49 FILE *p = fopen("a.dat", "r"); 50 if (p ==NULL) 51 return 0; 52 53 //fread(&m, 1, sizeof(struct man), p); 54 //fread(m, 3, sizeof(struct man), p); 55 56 int status = 0; 57 while (1) 58 { 59 fread(&m, 1, sizeof(struct man), p); 60 if (feof(p)) 61 break; 62 63 if (strcmp(name, "all") == 0) 64 { 65 printf("%s, %d ", m.name, m.age); 66 status = 1; 67 } 68 else 69 { 70 if (strcmp(name, m.name) == 0) 71 { 72 printf("%s, %d ", m.name, m.age); 73 status = 1; 74 } 75 } 76 } 77 /* 78 int i; 79 for (i = 0; i < 3; i++) 80 { 81 //printf("%s, %d ", m.name, m.age); 82 printf("%s, %d ", m[i].name, m[i].age); 83 } 84 */ 85 fclose(p); 86 if (status == 0) 87 printf("没有找到! "); 88 return 0; 89 } 90 //删除函数。 91 int mydelete() 92 { 93 FILE *p = fopen("a.dat", "r"); 94 if (p == NULL) 95 return 0; 96 97 //得到文件的大小。 98 fseek(p, 0, SEEK_END); 99 int size = ftell(p); 100 //文件多大就设置一个多大的堆空间。 101 struct man *m = malloc(size); 102 //一下子就把文件的所有内容读入堆内容。 103 fseek(p, 0, SEEK_SET); 104 fread(m, 1, size, p); 105 fclose(p); 106 //输入要删除的人的名字。 107 printf("请输入要删除人的名字:"); 108 char name[30] = { 0 }; 109 scanf("%s", name); 110 111 //得到有多少条记录。 112 int n = size / sizeof(struct man); 113 p = fopen("a.dat", "w"); 114 int i; 115 for (i = 0; i < n; i++) 116 { 117 if (strcmp(m[i].name, name) != 0) 118 fwrite(&m[i], 1, sizeof(struct man), p); 119 } 120 fclose(p); 121 free(m); 122 /* 123 //把所有的记录打印出来看一下。 124 int i; 125 for (i = 0; i < n; i++) 126 { 127 printf("%s, %d ", m[i].name, m[i].age); 128 } 129 */ 130 return 0; 131 } 132 //参数1代表写入,参数2代表读出。参数3代表删除。 133 int main(int argc, int **args) 134 { 135 if (argc < 2) 136 return 0; 137 char c = args[1][0]; 138 if (c == '1') 139 myinsert(); 140 if (c == '2') 141 myselect(); 142 if (c == '3') 143 mydelete(); 144 return 0; 145 }
=============================================================================