You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言读取二进制文件存入链表时输出空字符串及乱码数值问题咨询

问题原因分析
  • 读写方式不匹配:你以rb二进制模式打开文件,却使用fscanf(文本格式读取函数)解析内容。fscanf只能识别明文存储的字符串、十进制数字格式,二进制文件中存储的是内存直接导出的字节数据(比如int类型存的是4字节二进制值,不是ASCII数字串),完全不符合fscanf的解析规则,所以读取结果全是无效值,字符串为空、数值乱码都是这个原因导致的。
  • 重复读取逻辑错误:循环内连续调用了2次fscanf,每次循环会尝试读取2组数据,如果你本意是每次循环处理1个条目,这个逻辑本身就是错误的,会跳过一半数据,且读取失败后未做判断直接打印未初始化的变量值,也会输出乱码。
  • feof使用不规范:feof是在读取操作失败到达文件末尾后才会被置为真,你先判断!feof再执行读取,会导致最后一次读取时已经到达文件末尾,读取操作失败,直接打印未初始化的变量,出现异常值。
正确实现思路

如果你要读取的二进制文件是直接按item结构体的内存布局写入的(比如写入时用fwrite(&结构体变量, sizeof(item), 1, fp)写入),应该用fread直接读取结构体数据,示例修正代码如下:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct list_element
{
    char word[30];
    int l1;
    int l2;
    struct list_element *next;
} item;
typedef item *list;

int main()
{
    list L;
    list root = NULL;
    list *tail = &root; // 用于尾插保持读取顺序,头插逻辑可删除该变量
    FILE *f;
    if ((f = fopen("ImaFile.bin", "rb")) == NULL)
    {
        printf("can't open file\n");
        exit(-1);
    }
    puts("file opened successfully");

    item temp;
    // 每次读1个item大小的数据,读成功才进入处理逻辑
    while (fread(&temp, sizeof(item), 1, f) == 1)
    {
        printf("read content: word: %s, l1: %d, l2: %d\n", temp.word, temp.l1, temp.l2);
        // 申请节点存入链表
        L = malloc(sizeof(item));
        if (L == NULL) {
            perror("malloc failed");
            exit(-1);
        }
        memcpy(L, &temp, sizeof(item));
        L->next = NULL;
        *tail = L;
        tail = &L->next;
        // 如果要头插可替换上面4行为:
        // memcpy(L, &temp, sizeof(item));
        // L->next = root;
        // root = L;
    }

    fclose(f);
    // 此处可添加链表遍历代码验证存储结果
    return 0;
}
补充说明

如果你的ImaFile.bin本身就是明文文本格式,只是后缀名是bin,那你应该把打开模式换成r而不是rb,同时去掉重复的fscanf调用,修改feof的判断逻辑即可。

内容的提问来源于stack exchange,提问作者Ciao

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.11 04:30:00