第九章文件C语言程序设计一、C文件概述C程序与磁盘文件本章讨论的文件主要是指可供C程序在执行过程中从磁盘读取数据或写入数据的文件。磁盘文件分类按其存储方式,C文件可以分为:ASCII文件(文本文件)按数据的ASCII编码方式存放(可用文字编辑软件如“记事本”打开来看),如整数123存放在ASCII文件中将是’1’、’2’、’3’的字符序列,占3个字节的存储空间。二进制文件按数据在内存中存储的形式原样存放(0和1的集合),如整数123存放在二进制文件中,它的二进制数0000000001111011,即两个字节。流的概念C系统在处理这些文件时,并不区分类型,都看成是字符流(即以字节为存取单位)。输入输出字符流的开始和结束只由程序控制而不受物理符号(如回车符)的控制,故称“流式文件”。或者说流是对文件中数据的一个映射,相应文件的I/O操作对于编程者而言都是对流进行的,程序员只需与流打交道,写数据到流中和从流中读取数据。相似于文件类型,流也有两种:文本流和二进制流。缓冲文件系统C语言本身并不支持文件的输入和输出,它没有定义相关操作语句的关键字。其输入输出操作都是由系统库函数来完成的,这样有利于系统开发和移植。根据其对文件的操作的两种不同方式:缓冲I/O和非缓冲I/O,这些函数分成两组:一组叫“缓冲文件系统”,另一组叫“非缓冲文件系统”。我们只重点介绍缓冲文件系统。C程序与文件读写ANSIC提供四种读写文件的方法,通过四组函数进行:读写一个字符:读fgetc、写fputc读写一个字符串:读fgets、写fputs格式化读写:读fscanf、写fprintf读写一个“记录”(成“块”读写):读fread、写fwrite文件读写(文件操作)的基本步骤是:1、定义文件类型指针变量2、打开文件3、读写文件4、关闭文件二、文件操作文件打开/关闭程序的基本形式示例(设文件名为ABC.TXT):main(){FILE*fp;/*声明文件型指针变量*/…fp=fopen(“ABC.txt”,“w”);/*按指定文件使用方式打开文件*/…/*输入输出等*/fclose(fp);/*关闭文件*/}示例程序说明①FILE*fp;FILE是系统定义的结构体类型。P230②文件打开后,fp即代表该文件③通常需要判断该文件是否打开打开成功时,fopen()返回文件信息区的起始地址,失败则返回0(NULL)。if((fp=fopen(…))==NULL){printf(“打开失败”);exit(0);}示例程序说明(续)④文件使用方式P231表9.1基本方式是:r(只读)w(只写、创建)a(追加)加b:对二进制文件加+:读写注意:r和a要求该文件必须存在,否则出错(返回NULL)w为新建文件(如原来存在同名文件,被覆盖)二、文件操作文件的读写P232设文件指针变量为fp①单字符读写P233写入fputc(ch,fp)读入x=fgetc(fp)遇到文件末时,返回EOF(文件结束符,即-1)通常可用while(ch!=EOF)或while(!feof(fp))控制读取循环。P233比较:putchar(c)x=getchar()文件的读写(二)②字符串读写P234写入fputs(str,fp)读入fgets(str,n,fp)从fp所指文件中读入n-1个字节数据给字符数组str(未尾加’\0’,遇EOF即结束)比较:puts(str)gets(str)示例#includestdio.hFILE*fpr,*fpw;main(){charch;if((fpr=fopen(d:\\TEST.DAT,r))==NULL){printf(打开失败);exit(0);}if((fpw=fopen(d:\\abc.txt,“w))==NULL){printf(打开失败);exit(0);}ch=fgetc(fpr);while(ch!=EOF){printf(%c,ch);fputc(ch,fpw);ch=fgetc(fpr);}fclose(fpr);fclose(fpw);}运行之,打开两个文件观看结果。将fpw打开方式改为’a’后连续运行几次,看看abc.txt的结果。示例#includestdio.hFILE*fp;char*s=123;main(){charch;clrscr();if((fp=fopen(d:\\a.dat,“w+))==NULL){printf(文件打开失败);exit(0);}fgets(s,10,fp);puts(s);fputs(Hello,,fp);fputs(myfriends!,fp);fclose(fp);}运行之,打开文件a.dat观看结果。将fp打开方式改为’a+’后连续运行几次,看看结果。文件的读写(三)③格式化读写P235适用于一般实体,如数值型变量。fscanf(fp,“%d,%f”,&a,&b);将磁盘文件中的数据送给变量a,下一个送给变量bfprintf(fp,“%d,%6.2f”,a,b);将变量a和b按%d和%f格式输出到fp所指文件上比较:scanf(“%d,%f”,&a,&b);printf(“%d,%6.2f”,a,b);文件的读写(四)④读写一个“记录”(成“块”读写)P236适用于结构体等复杂实体。读入fread(p,size,n,fp)写入fwrite(p,size,n,fp)p-实体指针size-字节数n-多少次fp-文件指针调用成功,返回n值。示例:P237例8.5文件的定位文件中有一个位置指针,指向当前读写的位置。顺序读写一个文件时,每读写完一个字符,位置指针自动下移一个字符位置。以下函数可用于强制改变位置指针的位置。rewind(fp)使fp所指文件位置指针回到文件开头(以便从头再读写)fseek(fp,n,i)改变文件的位置指针关于fseek(fp,n,i)fp文件指针n位移量(以起始点为基点,向前移动的字节数,负数为倒移的字节数)i起始点函数ftell(fp)用于获得位置指针在文件中的当前位置(用相对于文件开头的位移量来表示)。[例9.7]使用rewind()函数改写[例8.5]。#includestdio.hmain(){FILE*fp;staticfloata[2][2]={0.1,2.3,4.5,6.7};floatb[4];inti;fp=fopen(“test”,“wb+”);fwrite(a,sizeof(float),4,fp);rewind(fp);fread(b+2,sizeof(float),2,fp);fread(b,sizeof(float),2,fp);for(i=0;i4;i++)printf(”%f%c”,b[i],i%2==1?’\n’:’’);fclose(fp);}示例以下程序的功能是。#includestdio.hmain(){FILE*fp;longintn;fp=fopen(wj.txt,rb);fseek(fp,0,SEEK_END);n=ftell(fp);fclose(fp);printf(%ld,n);}A)输出文件wj.txt的起始地址B)输出文件wj.txt的终止地址C)输出文件wj.txt的错误信息D)输出文件wj.txt的长度