对流式文件可以进行顺序读写,也可以进行随机读写,关键在于控制文件的位置指针。如果位置指针是按字节位置顺序移动的,就是顺序读写;如果能将位置指针按需要移动到任意的位置,就可以实现随机读写.所谓随机读写,是指读写完上一个字符(字节)后,并不一定要读写其后续的字符(字节),而可以读写文件中任意位置上所需要的字符(字节)。
用 fseek 函数可以实现改变文件的位置指针。
fseek 函数的调用形式为: fseek (文件类型指针,位移量,起始点)
“起始点 ”用0、1或 2 代替,0代表 “文件开始”,1 为“当前位置”,2 为 “文件末尾”。 ANSI C 标准指定的名字如下表所示:
起始点 名字 用数字代表
文件开始 SEEK_SET 0
文件当前位置 SEEK_ CUR 1
文件末尾 SEEK_END 2
“位移量”指以 “起始点” 为基点,向前移动的字节数。ANSI C 和大多数版本要求位移量是(long)长整型数据。这样当文件的长度大于64KB时不致出问题。ANSI C 标准规定在数字的末尾加一个字母 L,就表示是 long 型。
fseek 函数一般用于二进制文件,因为文本文件要发生字符转换,计算位置时往往会发生混乱。
下面是fseek 函数调用的几个例子:
fseek(fp,100L,0);/* 将位置指针移到离文件头100个字节处 */
fseek(fp,50L,1); /* 将位置指针移到离当前位置50个字节处 */
fseek(fp,--10L,2);/* 将位置指针从文件末尾处向后退 10 个字节 */
利用 fseek 函数就可以实现随机读写了。
例13.5 在磁盘文件上存有 10 个学生的数据。要求将第 1、3、5、7、9个学生数据输入计算机,并在屏幕上显示出来。程序如下:
#include "stdlib.h"
#include "stdio.h"
struct student_type
{
char name[10];
int num;
int age;
char sex;
}stud[10];
void main()
{
int a;
FILE * fp;
if((fp=fopen("stud_dat.txt","rb"))==NULL)
{
printf("can not open file\n");
exit(0);
}
for(a=0;a<10;a+=2)
{
fseek(fp,a * sizeof(struct student_type),0);
fread(&stud[a],sizeof(struct student_type),1,fp);
printf("%s %d %d %c\n",stud[a].name,stud[a].num,stud[a].age,stud[a].sex);
}
fclose(fp);
}
(先新建一个文本文件名为“stud_dat.txt”(可以改其它名字),然后在里面输入10学生的数据。接着再把本程序在VC编译系统中运行……)。
13.5.3 ftell 函数
ftell 函数的作用是得到流式文件中的当前位置,用相对文件开头的位移量来表示。由于文件中的位置指针经常移动,人们往往不容易知道其当前位置。
用 ftell 函数可以得到当前位置 。如果 ftell 函数返回值为--1L,表示出错。例如:
a=ftell(fp);
if(a==--1L)
printf("error\n");
变量 a 存放当前位置,如调用函数时出错(如不存在 fp 文件),则输出“error”。
tell(告诉,吩咐,断定,知道,)
例13.4 有一个磁盘文件,第一次将它的内容显示在屏幕上,第二次把它复制
#include "stdio.h"
void main()
{
FILE * fp1,* fp2;
fp1=fopen("file1.txt","r");
fp2=fopen("file2.txt","w");
while(! feof(fp1))
putchar(getc(fp1));
rewind(fp1);
while(! feof(fp1))
putc(getc(fp1),fp2);
fclose(fp1);
fclose(fp2);
}
例13.5 在磁盘文件上存有 10 个学生的数据。要求将第 1、3、5、7、9个学
#include "stdlib.h"
#include "stdio.h"
struct student_type
{
char name[10];
int num;
int age;
char sex;
}stud[10];
void main()
{
int a;
FILE * fp;
if((fp=fopen("stud_dat.txt","rb"))==NULL)
{
printf("can not open file\n");
exit(0);
}
for(a=0;a<10;a+=2)
{
fseek(fp,a * sizeof(struct student_type),0);
fread(&stud[a],sizeof(struct student_type),1,fp);
printf("%s %d %d %c\n",stud[a].name,stud[a].num,stud[a].age,stud[a].sex);
}
fclose(fp);
}
file1(文本文档里的内容)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)
stud_dat(文本文档里的内容)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)
Nu11 pointer assignment
(无效的) ( 指示器)(分配、任务、作业)