fscanf () в C, формат для строки переменной длины - PullRequest
1 голос
/ 18 февраля 2020

Итак, у меня есть файл, который содержит данные в виде:

...
5,25,15,16,1,3,Dwyfor_Meirionnydd
5,34,33,26,12,22,Gower
5,7,28,35,4,23,Islwyn
2,20,12,Llanelli
5,4,5,17,7,21,Merthyr_Tydfil_and_Rhymney
5,5,4,35,28,27,Monmouth
4,5,14,19,15,Montgomeryshire
7,0,32,17,5,12,20,33,Neath
2,38,24,Newport_East
...

И мне нужно прочитать каждую строку и поместить ее в структуру так, чтобы первое целое число без знака сохранялось, а следующее n без знака целые числа хранятся в массиве, а затем сохраняется строка в конце. Таким образом, в качестве примера, вторая строка будет выглядеть так:

number-of-elements: 5
array: {34,33,26,12,22}
name: "Gower"

* number сообщает нам, сколько элементов находится в array. У меня есть структура для этих данных. Как бы я go о создании формата для этого?

Ответы [ 2 ]

1 голос
/ 18 февраля 2020

Обычно вы просто используете отдельные вызовы fscanf в al oop для чтения элементов:

struct entry {
    int   data_size;
    int   *data;
    char  *name;
};


while (fscanf(input, "%d", &num) == 1) {
    struct entry *e = malloc(sizeof *e);
    e->data_size = num;
    e->data = malloc(num * sizeof e->data[0]);
    for (int i = 0; i < num; ++i) {
        if (fscanf(input, " ,%d", &e->data[i]) != 1) {
            fprintf(stderr, "Data format error\n");
            exit(1); } }
    if (fscanf(input, " ,%ms", &e->name) != 1) {
        fprintf(stderr, "Data format error\n");
        exit(1); }
    // read a record into 'e' -- store it into a data structure somewhere
}
0 голосов
/ 18 февраля 2020

Функция scanf не поддерживает переменное количество форматов. Вам нужно будет изменить то, что вы передаете функции в зависимости от количества элементов.

Лучший способ справиться с этим - прочитать строку, затем использовать strtok, чтобы разбить ее на токены, а затем использовать sscanf для анализа каждого отдельного элемента в al oop.

char line[100];
while (fgets(line, sizeof(line), fp)) {
    int count, i;
    int *array;
    char *name, *p;

    // read the count
    p = strtok(line, ",");
    sscanf(p, "%d", &count);

    // allocate space for the array
    array = malloc(count * sizeof(int));
    // read each element
    for (i=0; i<count; i++) {
        p = strtok(NULL, ",");
        sscanf(p, "%d", array + i);
    }

    // read the name
    p = strtok(NULL, "\n");
    name = strdup(p);

    // do something with count, array, and name
}

Обратите внимание, что это предполагает, что каждая строка в файле правильно сформирована и, следовательно, не проверяет формат.

...