我已将结构Student写入文件中,并将整个结构读取到控制台。
现在,我想重新定位文件指针以读取有关特定学生的信息。 我只想使用系统调用来写入文件(read(),write(),lseek())
这是用于将结构写入文件的代码:
struct Student{
char name[20];
char dob[20];
int id;
char sex[20];
};
struct Student stud[size];
for (int i = 0;i
printf("Enter name:");
scanf("%s",stud[i].name);
printf("Enter date of birth:");
scanf("%s",stud[i].dob);
printf("Enter id:");
scanf("%d",&stud[i].id);
printf("Enter sex:");
scanf("%s",stud[i].sex);
n =write(fd,&stud,sizeof(stud));
}
这是读取写入文件的整个结构的代码:
struct Student studread[5];
int j=0;
while (((n =read(fd,&studread, sizeof(studread))))){
printf("%s\",studread[j].name);
printf("%s\",studread[j].dob);
printf("%d\",studread[j].id);
printf("%s\",studread[j].sex);
j++;
}
这是读取有关特定学生信息的代码:
struct Student pread;
printf("Enter a position:");
scanf("%d",&pos);
nobytes =sizeof(struct Student) * pos-1;
position = lseek(fd,nobytes,SEEK_SET);
while (size=read(fd,&pread,sizeof(pread))){
printf("%s\",pread.name);
printf("%s\",pread.dob);
printf("%d\",pread.id);
printf("%s\",pread.sex);
}
您可以使用lseek()定位文件指针来帮助我从文件中读取特定学生的信息吗?
当您有if语句以5个方括号结尾时,您实际上可能会考虑重构代码。
同样,您也不保证read会真正读取所有请求的字节。 这就是为什么它返回正确读取(您正在忽略)的字节数的原因。
存在多个问题:
在您的编写循环中,您可能想要为一个索引为i的学生编写数据。同样,您应该使用结构Student的大小而不是所有学生的数据的完整大小。
在代码中,它看起来像这样:
n = write(fd, &stud[i], sizeof(struct Student));
这里&stud[i]指向学生i的数据。使用sizeof(struct Student)时,仅写入一个学生的数据。
将数据读入内存时,必须正确计算字节数。缺少一对括号。它应该看起来像:
nobytes = sizeof(struct Student) * (pos - 1);
如果只想输出一个学生,则应使用if而不是一会儿:
if (read(fd, &pread, sizeof(pread)) == sizeof(pread)) {
如果文件描述引用了normal file,则此行工作正常。
man 2 read说:
The system guarantees to read the number of bytes requested if the
descriptor references a normal file that has that many bytes left
before the end-of-file, but in no other case.
但是,如果使用网络文件系统,它可能已经失败。
因此,最好使用以下内容:
ssize_t bytes_read = 0;
ssize_t n;
while ((n = read(fd, &pread + bytes_read, sizeof(pread) - bytes_read)) > 0) {
bytes_read += n;
}
因此,如果read仅返回部分结果,则它也将正常工作。
不要忘记以后仍要检查读取的字节数。它可能看起来像:
if(bytes_read == sizeof(pread)) {
printf("%s\", pread.name);
printf("%s\", pread.dob);
printf("%d\", pread.id);
printf("%s\", pread.sex);
} else {
printf("not enough data");
exit(1);
}
好点子。 最好始终处理部分读取,即使引用了normal file。 我添加了更多信息。
感谢您的帮助。 史蒂芬(Stephan)发布的解决方案很棒,而且效果很好。 再次感谢。