读取文件串

时间:2016-01-29 23:18:40

标签: c file

我是C中的新手,我想创建一个程序,读取两个只包含字符串的输入文件。我已经创建了相关文件的字符串。我已经处理了一些问题,我无法弄清楚,那里有一些分段错误。 (由-ua问)

这是我的代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

typedef struct linked_list {
    char my_data[256];
    struct linked_list *next_it;
} node_t;

int main(int argc, char *argv[]) {  
    /*
    if(argc != 4) {
        fprintf(stderr, "Requiring 2 input 1 output file name to start!\n");
        exit(EXIT_FAILURE);
    }*/

    FILE *my_s;
    FILE *my_f;
    // FILE *my_o;
    bool mybool = true;
    int my_ch; // our char to read
    char my_buffer[256];
    bool check_all = true;

    node_t *set_a = malloc(sizeof(node_t));
    node_t *set_b = malloc(sizeof(node_t));
    my_f = fopen(argv[1], "r"); // first textfile to read
    my_s = fopen(argv[2], "r"); // second textfile to read

    if (my_f != NULL && my_s != NULL) {
        while (fgetc(my_f) != EOF && mybool != false && check_all != false) {
            my_ch = fgetc(my_f);
            int i = 0;
            while (my_ch >= 0) {
                my_buffer[i++] = my_ch;
                my_ch = fgetc(my_f);
            }
            strcpy(set_a->my_data, my_buffer);
            if (feof(my_f)) {
                mybool = false;
            } else {
                set_a->next_it = malloc(sizeof(node_t));
                set_a = set_a->next_it;
            }
        }
        mybool = false;
        printf("First File Copy Done!\n");
        while (fgetc(my_s) != EOF && mybool != true && check_all != false) {
            my_ch = fgetc(my_s);
            int i = 0;
            while (my_ch >= 0) {
                my_buffer[i++] = my_ch;
                my_ch = fgetc(my_s);
            }
            strcpy(set_b->my_data, my_buffer);
            if (feof(my_s)) {
                check_all = false;
            } else {
                set_b->next_it = malloc(sizeof(node_t));
                set_b = set_b->next_it;
            }
        }
        printf("Second File Copy Done!\n");
    } else {
        fprintf(stderr, "Cannot read from %s and %s\n", argv[1], argv[2]);
    }

    while (set_a != NULL) {
        int j = 0;
        printf("No: %d, Var: %s",j++, set_a->my_data);
        node_t *set_c = set_a;
        set_a = set_a->next_it;
        free(set_c);
    }
    while (set_b != NULL) {
        int j = 0;
        printf("No: %d, Var: %s",j++, set_b->my_data);
        node_t *set_c = set_b;
        set_b = set_b->next_it;
        free(set_c);
    }
    return 0;
}

2 个答案:

答案 0 :(得分:0)

在到达文件末尾之后,您没有将两个链接列表的尾部指向“NULL”,并且您没有保留每个链接列表的头部。每次读取字符串时都会改变头部。所以在最后阶段'set_a'和'set_b'成为没有NULL尾的最后一个节点

答案 1 :(得分:0)

您的代码有几个问题:

  • 使用未初始化的第一个节点初始化列表。无法在此节点中测试任何内容...为什么不将空列表初始化为NULL
  • 您通过读取每个文件的下一个字节来测试文件结尾,但是您不存储此字节...因此它会丢失。稍后您检查feof(my_s),但此功能不符合您的想法。检查fgetc()是否返回EOF要好得多,但要存储它读取的字节。
  • 为什么要使用mymy_启动每个本地变量名称,这没有帮助,只需使用短名称,它们不应该指定任何全局变量名称。
  • 你没有指向每个列表头部的指针,你设置set_aset_b指向下一个节点,再也找不到列表的头部了。
  • 您在打印和自由循环的每次迭代中将j重置为0,所有节点都将使用数字0进行打印。
  • 您应该使用函数来加载,打印和释放列表,以避免重复相同的代码两次。

以下是改进版本:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

typedef struct linked_list {
    char *data;
    struct linked_list *next;
} node_t;

node_t *load_lines(const char *filename) {
    node_t *head = NULL;
    FILE *fp = fopen(filename, "r");
    if (fp != NULL) {
        char buffer[256];
        size_t i = 0;
        int c;
        node_t **tailp = &head;

        for (;;) {
            c = fgetc(fp);
            if (c != EOF && c != '\n') {
                if (i < sizeof(buffer) - 1) {
                    buffer[i++] = c;
                }
                continue;
            }
            if (i > 0) {
                buffer[i] = '\0';
                /* allocate a new node */
                *tailp = malloc(sizeof(**tailp));
                (*tailp)->next = NULL;
                (*tailp)->data = strdup(buffer);
                tailp = &(*tailp)->next;
                i = 0;
            }
            if (c == EOF) {
                break;
            }
        }
        fclose(fp);
    }
    return head;
}

void print_word(node_t *np) {
    int j = 0;
    while (np != NULL) {
        printf("No: %d, Var: %s", j++, np->data);
        np = np->next;
    }
}

void free_words(node_t *np) {
    while (np != NULL) {
        node_t *next = np->next;
        free(np->data);
        free(np);
        np = next;
    }
}

int main(int argc, char *argv[]) {  
    /*
    if (argc != 4) {
        fprintf(stderr, "Requiring 2 input 1 output file name to start!\n");
        exit(EXIT_FAILURE);
    }*/

    node_t *set_a, *set_b;

    if ((set_a = load_words(argv[1])) != NULL) {
        printf("First File Copy Done!\n");
    }
    if ((set_b = load_words(argv[2])) != NULL) {
        printf("Second File Copy Done!\n");
    }
    if (!set_a && !set_b) {
        fprintf(stderr, "Cannot read from %s and %s\n", argv[1], argv[2]);
    }

    print_words(set_a);
    free_words(set_a);
    print_words(set_b);
    free_words(set_b);
    return 0;
}