2013-08-01 4 views
-1

Как разобрать строку из файла, который содержит символы и числа, в структуру typedef.Разбор строки в структуре typedef в C

Эти 2 строки являются примером данных, который должен быть проанализирован:

Pebbles Flintstone4Female 
Bam-Bam Rubble3Male 

Во-первых это имя, то пространство и следуют с фамилией, то возраст и пол.

Имя, фамилия, возраст и пол являются частями typedef, которые необходимо сохранить.

В общей сложности имеется семь строк, подобных тем, которые были сохранены в файле .txt.

Как написать правильный буфер для разделения строки?

Это то, что я получил так далеко

sscanf(buffer, "%[^ ]%*[^1234567890]%d%s", buff_name, buff_surname, buff_age, buff_gender); 

Но это, кажется, не работает должным образом, и я не могу получить доступ к любой информации о нем.

+3

Что именно не работает? Вы получаете какие-либо ошибки? Каков ваш ожидаемый результат и что вы видите? –

+0

Вы открыли файл? – Devolus

ответ

3
  1. Всегда проверяйте возвращаемое значение от sscanf() и его родственников.
  2. Включите предупреждения компилятора. Хороший компилятор расскажет вам о следующем выпуске:
  3. Не отменяйте назначение с помощью * в %*[0-9], если вы хотите, чтобы фамилия была прочитана.

Обратите внимание: ваша линия sscanf() не использует указанную структуру данных. Тем не менее, этот пример кода делает: выход

#include <stdio.h> 

typedef struct who 
{ 
    char name[20]; 
    char surname[20]; 
    int age; 
    char gender[7]; 
} who; 

int main(void) 
{ 
    const char *data[2] = 
    { 
     "Pebbles Flintstone4Female", 
     "Bam-Bam Rubble3Male", 
    }; 
    const char *fmt[2] = 
    { 
     "%[^ ]%*[^1234567890]%d%s", 
     "%[^ ]%[^1234567890]%d%s", 
    }; 

    for (int i = 0; i < 2; i++) 
    { 
     for (int j = 0; j < 2; j++) 
     { 
      who buff; 
      int n; 
      if ((n = sscanf(data[j], fmt[i], buff.name, buff.surname, &buff.age, buff.gender)) != 4) 
       printf("Oops: format \"%s\", n = %d: %s\n", fmt[i], n, data[j]); 
      else 
       printf("Format \"%s\": data %s: %s %s %d %s\n", 
         fmt[i], data[j], buff.name, buff.surname, buff.age, buff.gender); 
     } 
    } 
    return 0; 
} 

Пример:

Oops: format "%[^ ]%*[^1234567890]%d%s", n = 3: Pebbles Flintstone4Female 
Oops: format "%[^ ]%*[^1234567890]%d%s", n = 3: Bam-Bam Rubble3Male 
Format "%[^ ]%[^1234567890]%d%s": data Pebbles Flintstone4Female: Pebbles Flintstone 4 Female 
Format "%[^ ]%[^1234567890]%d%s": data Bam-Bam Rubble3Male: Bam-Bam Rubble 3 Male 

Если вы компилируете с строкового литерала для формата sscanf(), GCC будет предупреждать вас об этой проблеме:

td.c: In function ‘main’: 
td.c:23: warning: format ‘%d’ expects type ‘int *’, but argument 4 has type ‘char *’ 
td.c:23: warning: format ‘%s’ expects type ‘char *’, but argument 5 has type ‘int *’ 
td.c:23: warning: too many arguments for format 

Код выше с разными строками формата не может дать вам это предупреждение.

строки формата должны быть изменены, чтобы избежать переполнения буфера, тоже:

"%19[^ ] %19[^0-9] %d %6s"