C文件相关操作

来源:互联网 发布:linux 怎么读 编辑:程序博客网 时间:2024/06/08 06:33

 

第一部分 文件的打开和关闭

1.1文件指针

  C语言中用一个指针变量指向一个文件,这个指针成为文件指针。通过文件指针,可以对它所指的文件进行各种操作。

  定义文件指针的一般格式为:

   FILE * 指针变量标识符;

 其中FILE应为大写,它实际上是由系统定义的一个结构,该结构中含有文件名、文件状态和文件当前位置等信息。在编写源程序时不必关系FILE结构的细节。

 如:

    FILE * fp;

  表示fp是指向FILE结构的指针变量,通过fp即可查找存放某个文件信息的结构变量,然后按结构变量提供的信息找到该文件,实施对文件的操作。习惯上把fp称为指向一个文件的指针。

1.2文件的打开与关闭具体操作

  文件在进行读写操作之前要先打开,使用完毕要关闭。所为打开文件,实际上是建立文件的各种有关信息,并使文件指针指向该文件,以便进行各种其他操作。关闭文件则断开指针与文件之间的联系,也就是禁止再对该文件进行操作。

 A.文件的打开(fopen()函数)

  fopen()函数用来打开一个文件,其调用的一边形式为:

     文件指针名=fopen(文件名,使用文件方式)

  其中:

 1文件指针名必须是被说明为FILE类型的指针变量。

 2文件名是被打开文件的文件名,是字符串变量或字符串数组。

 3使用文件方式是指文件的类型和操作要求。

  如:

    FILE * fp;

    fp=("file a","r");

   其意义是在当前目录下打开文件file a,但只允许对文件进行操作,并使fp指向该文件。

 

  文件的使用方式共有12中,如下表:

 

文件使用方式

意义

“rt”

以只读形式打开一个文本文件,只允许读数据

“wt”

以只读形式打开或建立一个文本文件,只允许读数据

“at”

以追加形式打开一个文本文件,并在文件末尾写数据

“rb”

以只读形式打开一个二进制文件,只允许读数据

“wb”

以只读形式打开或建立一个二进制文件,只允许读数据

“ab”

以追加形式打开一个二进制文件,并在文件末尾写数据

“rt+”

以读写形式打开一个文本文件,允许读写

“wt+”

以读写形式打开或建立一个文本文件,允许读写

“at+”

以读写形式打开一个文本文件,允许读,或在文件末尾追加数据

“rb+”

以读写形式打开一个二进制文件,允许读写

“wb+”

以读写形式打开或建立一个二进制文件,允许读写

“ab+”

以读写形式打开一个二进制文件,允许读,或在文件末尾追加数据

 对于文件使用方式有以下几点说明:

 1)文件使用方式由rwatb+6个字符组成。其中t为文本文件,可省略不写。

 2)凡用“r”方式打开一个文件,进行读操作时,该文件必须存在,且只能从该文件读出数据。

 3)用“w”方式打开文件,进行写操作时,只能向文件写入数据。若打开的文件不存在,则以指定的文件名建立新文件,若打开的文件已经存在,则将该文件删除,重新建立一个新文件。

 4)若要向一个已存在的文件追加新信息,只能用“a”方式打开文件。但此时该文件必须是存在的,否则将会出错。

 5)在打开一个文件时,如果出错,fopen函数将返回一个空指针NULL。在程序中可以用这一信息来判断是否完成打开文件的操作,并作相应的处理。

 6)打开文件常用程序段

  if(fp=fopen("c://CYYXX","rb")==NULL)

   {printf("/nerror on open c://CYYXX file!"); getch(); exit(1);}

 这段程序的意义是,如果返回的指针为空“NULL”,表示不能打开C盘根目录下的CYYXX文件,则给出提示信息error on open c://CYYXX file!,下一行getch()的功能是当用户按下键盘上的任意键时,程序才继续执行,因此用户可利用这个等待时间阅读出错提示。按任意键后执行exit(1)退出程序。

 7)把一个文本文件读入内存时,要将ASCII码转换成二进制码,而要把文件以文本方式写入磁盘时,也要把二进制码转换成ASCII码,因此对文本文件的读写操作要花费较多的转换时间。对二进制文件执行读写操作时不存在这种转换。

 B.文件关闭函数(fclose()函数)

  文件一旦使用完毕,可用关闭文件函数把指定文件关闭,以避免文件数据的丢失等错误的发生。

  fclose()函数调用的一般形式为:

   fclose(文件指针);

  如:

   fclose(fp);

 正常完成关闭文件操作时,fclose函数返回值为0。如返回值为非零值则表示有错误发生。

1判断stu.txt文件能否以只读方式打开,并返回相应的提示信息。

 

#include<stdio.h> 

#include<string.h>

main(){

FILE *fp;

fp=fopen("D://充实的//Visual C 工作目录//stu.txt","r");

if(fp==NULL)

printf("Filecannot be open/n");

else

{

printf("File canbe open/n");

fclose(fp);

}

}

 

 

2打开和关闭一个可读可写的二进制文件。

 

#include<stdio.h> 

#include<string.h>

main(){

FILE *fp;

fp=fopen("D://充实的//Visual C 工作目录//test.dat","rb+");

if(fp==NULL)

{

printf("Filecannot be open/n");

exit(1);

}

else

printf("file canbe open/n");

 

if(fclose(fp))

printf("fileclose error/n");

}

  第二部分 文件的读写

 对文件的读和写是最常用的文件操作。在C语言中提供了多种文件读写的函数。

 1)字符读写函数:fgetcfputc

 2)字符串读写函数:fgetsfputs

 3)数据块读写函数:freadfwrite

 4)格式化读写函数:fscanffprintf

 2.1字符读写函数fgetcfputc

 字符读写函数是以字符(字节)为单位的读写函数。每次可从文件读取或向文件写入一个字符。

 A.读字符函数fgetc()

 fgetc函数的功能是从指定的文件中读一个字符,函数调用的形式为:

   字符变量=fgetc(文件指针);

 :

  ch=fgetc(fp);

 其意思是从打开的文件fp中读取一个字符并送入ch中。

 对于fgetc()函数的使用方法,有以下几点说明:

 1)在fgetc()函数调用中,读取的文件必须是以读(r)或读写(r+)方式打开的。

 2)读取字符后,也可以不向字符变量赋值。

  如:

   fgetc(fp);

  但读出的字符不能保存。

  3)在文件内部有一个位置指针。用来指向文件的当前读取字节。在文件打开时,该指针总是指向文件的第一个字节。使用fgetc函数后,该位置指针将向后移动一个字节。因此可以连续多次使用fgetc函数,读取多个字符。应注意文件指针和文件内部的位置指针不是一回事。文件指针是指向整个文件的,需在程序中说明,只要不重复赋值,文件指针的值是不变的。文件内部的位置指针用以指示文件内部的当前读写位置,每读写一次,该指针向后移动一个字节,它不需在程序中定义说明,有系统自动设置。

3读取文件c1.txt中的数据,并在屏幕上输出。

 

#include<stdio.h> 

#include<string.h>

main(){

FILE *fp;

char ch;

fp=fopen("D://充实的//Visual C 工作目录//c1.txt","rb+");

if(fp==NULL)

{

printf("Filecannot be open/n");

exit(1);

}

ch=fgetc(fp);

 

while(ch!=EOF)

{

putchar(ch);//putchar函数(字符输出函数)的作用是向终端输出一个字符。

ch=fgetc(fp);

}

fclose(fp);

}

  只要读出的字符不是文件结束标志(每个文件末都有一结束标志EOF)就把字符显示在屏幕上,再读入下一个字符。每读一次,文件内部的位置指针向后移动一个字节,文件结束时,该指针指向EOF。执行本程序将显示整个文件。

 

B.写字符函数fputc()

 fputc函数的功能是把一个字符写入指定的文件中,函数调用的形式为:

   fputc(字符量,文件指针);

 其中,待写入的字符量可以是字符常量或变量,如:

 fputc('a',fp);

 其意义是把字符a写入fp所指向的文件中。

 对于fputc()函数的使用,有以下几点说明:

 1)被写入的文件可以用写、读写或追加的方式打开,用写或读写方式打开一个已存在文件时将清除原有文件内容,写入字符从文件头开始。如需保留原有文件内容,希望写入的字符从文件末尾开始存放,必须以追加方式打开文件。被写入的文件若不存在,则创建该文件。

 2)每写入一个字符,文件内部位置指针向后移动一个字节。

 3fputc()函数有一个返回值,如写入成功则返回写入的字符,否则返回EOF。可以由此来判断写入是否成功。

4通过键盘输入一行字符,写入一个文件(string),再把该文件内容读出,并显示在屏幕上。

 

#include<stdio.h> 

#include<string.h>

main(){

FILE * fp;

char ch;

if((fp=fopen("D://充实的//Visual C 工作目录//string.txt","wt+"))==NULL)

{

printf("filecannot open");

exit(0);

}

printf("pleaseinput a string:/n");

ch=getchar();

while(ch!='/n')

{

fputc(ch,fp);

ch=getchar();

}

rewind(fp);

ch=fgetc(fp);

while(ch!=EOF)

{

putchar(ch);

ch=fgetc(fp);

}

printf("/n");

fclose(fp);

}

 rewind()函数用于把fp所指文件的内容位置指针移到文件头。

 2.2  字符串读写函数fgets()fputs()

A.字符串读写函数fgets()fputs()

  函数的功能是指从指定的文件中读取一个字符串到字符数组中,函数调用的形式为:

     fgets(字符数组名,n,文件指针);

  其中n是一个正整数。表示从文件中读出的字符串不超过n-1个字符串。在读取最后一个字符后加上串结束标志'/0'

  如:

    fgets(str,n,fp);

 意思是从fp所指的文件中读取n-1个字符,送入字符数组str中。

5string文件中读取一个包含10个字符的字符串。

#include<stdio.h> 

#include<string.h>

main(){

char str[11];

FILE * fp;

if((fp=fopen("D://充实的//Visual C 工作目录//string.txt","rt"))==NULL)

{

printf("file cannotopen!/n");

getch();//getch();会等待你按下任意键,再继续执行下面的语句;

exit(0);//正常退出;exit(1)异常退出

}

fgets(str,11,fp);

printf("/n%s/n",str);

fclose(fp);

}

  本例定义了一个字符数组str,长度为11个字节,在以读文本文件方式打开文件string后,从中读取10个字符,送入str数组中,在数组最后一个单元内将加上'/0',然后在屏幕上显示输出str数组。

  fgets函数有两点说明:

  1)在读出n-1个字符之前,如遇到了换行符或EOF,则读操作结束。

  (2)fgets函数也有返回值,其返回值是字符数组的首地址。

 

 B.写字符串fputs()

 fputs函数的功能是向指定的文件写入一个字符串,其调用形式为:

  fputs(字符串,文件指针);

 其中字符串可以是字符串常量,也可以是字符串数组名,或指针变量,如:fputs("abcd",fp);

其意思是把字符串"abcd"写入fp所指的文件之中。

 6string文件中追加一个字符串。

#include <stdio.h> 

#include<string.h>

main(){

char str[20],ch;

FILE * fp;

if((fp=fopen("D://充实的//Visual C 工作目录//string.txt","at+"))==NULL)

{

printf("filecannot open!/n");

getch();//getch();会等待你按下任意键,再继续执行下面的语句;

exit(1);//正常退出;exit(1)异常退出

}

printf("pleaseinput a string!/n");

scanf("%s",str);

fputs(str,fp);

rewind(fp);

ch=fgetc(fp);

while(ch!=EOF){

putchar(ch);

ch=fgetc(fp);

}

printf("/n");

fclose(fp);

}

 7从一个文本文件test1.txt中读出字符串,在写入另一个文件test2.txt中。

#include<stdio.h> 

#include<string.h>

main(){

char str[128];

FILE * fp1,*fp2;

if((fp1=fopen("D://充实的//Visual C 工作目录//test1.txt","r"))==NULL)

{

printf("filecannot open!/n");

getch();//getch();会等待你按下任意键,再继续执行下面的语句;

exit(1);//正常退出;exit(1)异常退出

}

if((fp2=fopen("D://充实的//Visual C 工作目录//test2.txt","w"))==NULL)

{

printf("filecannot open!/n");

getch();//getch();会等待你按下任意键,再继续执行下面的语句;

exit(1);//正常退出;exit(1)异常退出

}

if(strlen(fgets(str,128,fp1))>0)//从文件中读回的字符串长度大于0

{

fputs(str,fp2);//从文件1读字符串,并写到文件2

printf("%s",str);//在屏幕上显示

}

fclose(fp1);

fclose(fp2);

}

 2.3 数据块读写函数fread()fwrite()

 C语言还提供了整块数据的读写函数。可用来读写一组数据,如一个数组元素,一个结构变量的值等。

 读数据块函数调用的一般形式为:

  fread(buffer,size,count,fp);

 写数据块函数调用的一般格式为:

  fwrite(buffer,size,count,fp);

 其中:

 1buffer是一个指针,在fread函数中,它表示存放输入数据的首地址。在fwrite函数中,它表示存放输入数据的首地址。

 2size表示数据块的字节数。

 3count表示要读写的数据块块数。

 4fp表示文件指针。

 如:

    fread(fa,4,5,fp);

 其意思是从fp所指的文件中,每次读取4个字节(一个实数),送入实数组fa中,连续读5次,即读取5个实数到fa中。

 8通过键盘输入两个学生数据,写入一个文件中,再读出这两个学生的数据,显示在屏幕上。

 

#include<stdio.h> 

#include<string.h>

struct stu{

char name[10];

int num;

int age;

char addr[15];

}boya[2],boyb[2],*pp,*qq;

 

main(){

FILE *fp;

int i;

pp=boya;

qq=boyb;

if((fp=fopen("D://充实的//Visual C 工作目录//test1.txt","wt+"))==NULL)

{

printf("filecannot open!/n");

getch();

exit(1);

}

printf("/npleaseinput data!/n");

for(i=0;i<2;i++,pp++)

scanf("%s%d%d%s",pp->name,&pp->num,&pp->age,pp->addr);//boya数组中输入数据,scanf参数的最后不要加/n

pp=boya;

fwrite(pp,sizeof(structstu),2,fp);

rewind(fp);

fread(qq,sizeof(structstu),2,fp);

i=0;

printf("/nname/tnum    age     addr/n"); 

for(i=0;i<2;i++,qq++)

printf("%s/t%5d%7d  %s/n",qq->name,qq->num,qq->age,qq->addr);

fclose(fp);

}

  本例程序定义了一个结构体stu,说明了两个结构体数组boyaboyb及两个结构指针变量ppqqpp指向boyaqq指向boyb

  24  格式化读写函数fscanf()fprintf()

  fscanf()函数,fprintf()函数与前面是用的scanf()printf()函数的功能相似,都是格式化读写函数。两者的区别在于fscanf()函数和fprintf()函数的读写对象不是键盘和显示器,而是磁盘文件。

  fscanffprintf函数的调用格式为:

   fsccanf(文件指针,格式字符串,输入列表);

   fprintf(文件指针,格式字符串,输入列表);

 如:

  fscanf(fp,"%d%s",&i,s);

   fprintf(fp,"%d%c",j,ch);

 9将一些格式化的数据写入文本文件,再从该文件中以格式化方法读出显示到屏幕上,其格式化数据为两个学生记录,包括姓名、学号和两科成绩。

 #include <stdio.h> 

#include<string.h>

struct stu{//定义结构体

char name[10];

char num[10];

float score1;

float score2;

}student;

 

main(){

FILE *fp;//定义指针

int i;

if((fp=fopen("D://充实的//Visual C 工作目录//test1.txt","wt"))==NULL)//判断能否打开文件

{

printf("file cannot open!/n");

exit(0);

}

printf("/nplease input data!/n");//输入文件内容

for(i=0;i<2;i++)

{

scanf("%s%s%f%f",student.name,student.num,&student.score1,&student.score2);

//通过键盘输入

fprintf(fp,"%s  %s%7.2f%7.2f/n",student.name,student.num,student.score1,student.score2);

//写入文件

}

fclose(fp);//关闭文件

 

if((fp=fopen("D://充实的//Visual C 工作目录//test1.txt","rt"))==NULL)

{

printf("file cannot open!/n");

getch();

exit(1);

}

while(fscanf(fp,"%s%s%f%f/n",student.name,student.num,&student.score1,&student.score2)!=EOF)//从文件读入

{

printf("%s  %s%  7.2f%7.2f/n",student.name,student.num,student.score1,student.score2);//显示到屏幕上

}

 

fclose(fp);

}

 第三部分 文件的随机读写

 随机读写方式是指移动文件内部的位置指针到需要读写的位置,在进行读写。按照要求移动位置指针的操作成为文件的定位。

 3.1 文件定位

  移动文件内部位置指针的函数主要有两个,即rewind函数和fseek函数。

  rewind函数前面多次使用,其调用形式为:

    rewind(文件指针);

  它的功能是把文件内部的位置指针移到文件首。

  下面主要介绍fseek函数。fseek函数用来移动文件内部位置指针,其调用形式为:

    fseek(文件指针,位移量,起始点);

  其中:

  (1)“文件指针”指向被移动的文件。

  (2)“位移量”表示移动的字节数,要求位移量是long型数据,以便在文件长度大于64KB时不会出错。当用常量表示位移量时,要求加后缀“L”。

   (3)“起始点”表示从何处开始计算位移量,规定的起始点有3中:文件首,当前位置和文件尾。

  其表示方法如下表所示:

 

起始点

表示符号

数字表示

文件首

SEEK_SET

0

当前位置

SEEK_CUR

1

文件末尾

SEEK_END

2

如:

   fseek(fp,100L,0);

  其意义是把位置指针移到距离文件首100个字节处。

  还要说明的是fseek函数一般用于二进制文件。在文本文件中由于要进行转换,故往往计算的位置会出现错误。

 3.2  文件的随机读写具体操作方法

  在移动位置指针之后,即可使用前面介绍的任一种读写函数进行读写。由于一般是读写一个数据块,因此常用fread和fwrite函数。

 例10:使用随机读取文件

 

#include<stdio.h>#include<stdlib.h>#define NUM 20main( ){    FILE *fp1; /*定义文件指针*/    char *temp;    int i,j;    struct rec{ /*定义结构体类型*/        char id[10];        char name[15];        char department[15];    }record[NUM];         printf("***********************************************************/n");    printf("** This program is to show the random file input & output**/n");    printf("***********************************************************/n");     if ((fp1=fopen("d://infile.txt","wb"))==NULL) /*以二进制只写方式打开文件*/    {    printf("cannot open file");/*出错返回*/    exit(1);    }    for( i=0;i<NUM;i++)    {    printf("Please input id:");    scanf("%s",record[i].id); /*从键盘输入*/    printf("Please input name:");     scanf("%s",record[i].name);    printf("Please input department:");     scanf("%s",record[i].department);    fwrite(&record[i],sizeof(struct rec),1,fp1); /* 成块写入*/    }    fclose(fp1); /*关闭*/    if((fp1=fopen("d://infile.txt","rb+"))==NULL)/*以可读写方式打开文件*/    {    printf("cannot open file"); /*出错返回*/    exit(1);    }    printf("************************************/n");    printf("%-10s%-15s%-15s/n","id","name","department");    printf("************************************/n");    for (i=0;i<NUM;i++)    { /*显示全部文件内容*/    fread(&record[i],sizeof(struct rec),1,fp1);    printf("%-10s%-15s%-15s/n",record[i].id,record[i].name,record[i].department);    }    /*以下进行文件的随机读写*/    fseek(fp1,2*sizeof(struct rec),0); /* 定位文件指针指向第三条记录*/    fwrite(&record[1],sizeof(struct rec),1,fp1);    /* 在第三条记录处写入第二条记录*/    rewind(fp1); /*移动文件指针到文件头*/    printf("************************************/n");    printf("%-10s%-15s%-15s/n","id","name","department");    printf("************************************/n");    for (i=0;i<NUM;i++)    { /*重新输出文件内容*/    fread(&record[i],sizeof(struct rec),1,fp1);    printf("%-10s%-15s%-15s/n",record[i].id,record[i].name,record[i].department);    }    fclose(fp1); /*关闭文件*/     scanf("%d",i);}
3.3  文件检测函数

C语言常用的文件检测函数有以下几个:

1.文件结束检测函数feof

  feof(文件指针);

  功能:判断文件是否处于文件结束为止,如文件结束,则返回值1,否则返回值0.

2.读写文件出错检测函数ferror

ferror函数的调用格式为:

   ferror(文件指针);

 功能:检查文件在用各种输入输出函数进行读写时是否出错。如ferror的返回值为0,表示未出错,否则表示有错。

3.文件出错标志和文件结束置0函数

clearerr函数的调用格式:

  clearerr(文件指针);

 功能:本函数用于清除出错标志和文件结束标志,使他们为0值。

 

原创粉丝点击