2014-12-10 115 views
2

我正在测试二进制文件I/O。所以,练习我做了一个小程序:fwrite打印垃圾,fread读取垃圾结构

的main.c:

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include "person.h" 

int main() 
{ 
    struct person me; 
    struct person cpy_me; 
    FILE *dataWrite, *dataRead; 

    strcpy(me.fname, "john"); 
    strcpy(me.lname, "smith"); 
    me.age = 12; 

    printf("%s %s %d\n", me.fname, me.lname, me.age); 

    dataWrite = fopen("people.bin", "wb"); 
    if (fwrite(&me, sizeof(struct person), 1, dataWrite) != 1) 
     fprintf(stderr, "Error!\n"); 
    printf("Wrote to the file\n"); 

    dataRead = fopen("people.bin", "rb"); 

    fread(&cpy_me, sizeof(struct person), 1, dataRead); 
    printf("%s->Fname\n", cpy_me.fname); 
    printf("%s->Lname\n", cpy_me.lname); 
    printf("%d->Age\n", cpy_me.age); 

    fclose(dataWrite); 
    fclose(dataRead); 

    return 0; 
} 

person.h:

#ifndef PERSON_H_INCLUDED 
#define PERSON_H_INCLUDED 

#define MAXFIRST 10 
#define MAXLAST  20 

struct person 
{ 
    char lname[MAXLAST], fname[MAXFIRST]; 
    int age; 
}; 
#endif // PERSON_H_INCLUDED 

这是出现在文件中people.bin

smith ÿÿb¸tÄ[½tà@ john @ à@          

当我阅读显示fread的结果时,我得到:

enter image description here 我知道在二进制文件中,它不会以人类可读的形式显示它,但它应该看起来像这样吗?我不这么认为,因为年龄甚至不可见,fread显示它读取垃圾。

+3

'FCLOSE(数据);数据=的fopen( “people.bin”, “RB”); FREAD(cpy_me,...' – BLUEPIXY 2014-12-10 23:12:42

+0

现在我得到这样的:'史密斯ÿÿb¸tÄ[½tà@约翰@à@ ' – stackptr 2014-12-10 23:16:46

+0

对我很好用 – BLUEPIXY 2014-12-10 23:19:30

回答

2

此代码片段有两个单独的问题:首先,因为BLUEPIXY已经评论过,您需要关闭并重新打开或倒带文件,然后再次读取它。否则,您的fread()将失败,并且由于您未在程序中检查错误,因此只有在您尝试打印cpy_me内的字符串时才会注意到这些字符串,这些字符串保持未初始化状态。

这会问题二:确保初始化结构me为零,例如,通过做struct person me = {"", "", 0};这应该照顾你在二进制文件中看到的垃圾。 C中的结构不会自动初始化,除非它们是全局变量,或者您明确地告诉编译器这样做。注意,像这样做二进制I/O是不可移植的,因为结构可能在不同的体系结构上有不同的内存布局(要想看到这一点,请尝试在32位和64位模式下重新编译并比较你的程序生成的二进制文件)。