第十三章:文件输入/输出
编写程序,对文件的操作是肯定会遇到的,无论是使用那种语言,都可能会遇到这样类似的需求,因为系统的目的是为人们日常生产生活提供便利,难免会遇到文件的使用。在这一章,我们便学习并了解一下文件在程序里面应该如何去使用。
C语言提供两种访问文件的途径:二进制模式和文本模式。在二进制模式中,程序可以访问文件的每个字节。而在文本模式中,程序所见的内容和文件的实际内容不同,程序以文本模式读取文件时,会把本地环境表示的行末尾或文件结尾映射为C模式。
I/O的两个级别:底层I/O使用操作系统提供的基本I/O服务。标准高级I/O使用C库的标准包和stdio.h头文件定义。
标准文件:C程序会自动打开三个文件,它们被称为标准输入、标准输出和标准错误输出。默认情况下,标准输入是系统的普通输入设备,通常为键盘;标准输出和标准错误输出是系统的普通输出设备,通常为显示屏。
标准I/O的好处;第一,它有许多专门的函数简化了处理不同I/O的问题。第二,输入和输出都是缓冲的。
exit()函数:关闭所有打开的文件并结束程序。通常的惯例是:正常结束的程序传递0,异常结束的程序传递非零值。标准要求0或宏定义EXIT_SUCCESS用于表明成功结束程序,宏EXIT_FAILURE用于表明结束程序失败,这些宏以及函数原型都位于stdlib.h头文件中。如果main()函数在一个递归程序中,exit()仍然会终止程序,但是return只会把控制权交给上一级递归,直至最初的一级。然后return结束程序。在所有函数中,包括递归之内,调用exit()都会结束这个程序。
fopen()函数:第一个参数是待打开文件的名称,确切的说是一个包含该文件名的字符串地址。第二个参数是一个字符串,指定待打开文件的模式。成功打开文件之后,fopen返回文件指针,其他I/O函数可以根据这个指针指定该文件,文件指针的类型是指向FILE的指针。
getc()函数:从指定的文件中获取一个字符,参数为指定的文件。
putc()函数:把字符放到指定的文件中,第一个参数是待写入的字符,第二个是文件指针。
fclose()函数:关闭指定的文件,必要时刷新缓冲区,如果成功关闭文件,函数返回0,否则,返回EOF,磁盘已满、移动硬盘被移除或出现I/O错误,都会导致调用该函数失败。
fprintf()函数:类似于sprintf()函数。第一个参数为要写入的文件地址,第二个为字符串,第三个如果有必要为字符串中的内容赋值。
fscanf()函数:将文件中的内容读取到后面指定的地址中,通过转换说明说明格式。
rewind()函数:返回到文件的开始处。
fgets()函数:第一个参数为存储输入位置的地址,第二个参数表示待输入字符串的大小,第三个参数指定要读取的文件。遇到EOF时返回NULL值,可以用于检查是否到达文件结尾,未遇到EOF会返回之前传给它的第一个参数。
fputs()函数:配合fget()函数一起使用。第一个参数表示字符串的地址,第二个参数指定目标文件。
fseek()函数:第一个参数指向待查找的文件,第二个参数是偏移量,long类型,正-前移、负-后移或0-保持不动,第三个参数是模式,确定起始点,有几个常用明示常量,SEEK_SET表示文件开始处,SEEK_CUR表示当前位置,SEEK_END表示文件末尾。正常,该函数返回值为0,如果出现错误,返回值为-1。
ftell()函数:返回类型是long,返回的是参数指向文件的当前位置距离文件开始处的字节数。
fgetpos()函数和fsetpos()函数:fseek和ftell函数的潜在问题是将文件大小限制在long类型能表示的范围内,,为了处理较大的文件,新增的新定位函数,不使用long类型表示位置,使用一种新类型,fpos_t(文件定位类型)。fgetpos()函数:第一个参数为文件指针,第二个参数指向fpos_t类型的值的指针,该函数会将fpos_t类型的值放在第二个参数的位置,该值描述了文件中的当前位置距离文件开头的字节数。如果成功返回0,失败返回非零值。fsetpos()函数的第一个参数为文件指针,第二个参数为调用fgetpos()函数获得的值,调用函数后,文件指针向后偏移相应的值,如果成功返回0,如果失败,返回非零值。
ungetc()函数:将指定的字符放回到输入流中,如果把一个字符放回输入流中,下次调用标准输入函数时将读取该字符。
fflush()函数:将输入缓冲区中的所有未写入数据发送到参数指定的输出文件,刷新缓冲区,如果参数是空指针,所有输出缓冲区都被刷新。
setvbuf()函数:创建一个供标准I/O函数替换使用的缓冲区。在打开文件之后且未对流进行其他操作之前,调用该函数。第一个参数为文件指针,识别待处理的流。第二个参数指向待使用的存储区,如果值不为NULL,则必须创建一个缓冲区,如果为NULL的话,该函数会为自己分配一个缓冲区。第三个参数有以下选择:_IOFBF表示完全缓冲(缓冲区满时刷新);_IOLBF表示行缓冲(在缓冲区满时或写入一个换行符时);_IONBF表示无缓冲。第四个参数告诉函数需要处理数据的大小,如果函数操作成功,返回0,否则返回一个非零值。
fwrite()函数:把二进制数据写入文件。第一个参数是待写入数据块的地址。size表示待写入数据块的大小,第三个参数表示待写入数据块的数量,第四个参数指定要写入的文件。返回成功写入项的数量。正常情况下,应该和第三个参数一致,但是如果写入错误,返回值会比第三个参数小。
fread()函数:用于读取被fwrite函数写入文件的数据。第一个参数是待读取文件数据在内存中的地址,第二个参数表示数据块的大小,第三个参数表示数据块的数量,第四个参数指定待读取的文件。返回成功读取项的数量。正常情况下,应该和第三个参数一致,但是如果写入错误,返回值会比第三个参数小。
feof()函数和ferror()函数:如果标准输入函数返回EOF,则通常表明函数已到达文件结尾。然而,出现读取错误时,函数也会返回EOF。这两个函数用于区分这两种情况。当上一次输入调用检测到文件结尾时,feof()函数返回一个非零值,否则,返回0。当读或写出现错误,ferror()函数返回一个非零值,否则返回0。