Как указал @chux в своем ответе, ключ правильно сопоставляет строку формата с данными, которые должны быть проанализированы, а затем критически проверяет возвращаемое значение по сравнению с ожидаемым числом преобразований. Основные ошибки в вашей строке формата - это ненужное включение %*s
(чтобы попытаться пропустить "("
) и %s %*s
(чтобы попытаться пропустить запятую) и %s%*s %*s
(чтобы попытаться и пропустите ") "
в нескольких местах, что приведет к чтению чтения и отбрасыванию всего первого числа, например, "(1231212A,"
в виде строки, начало чтения значений во второй группе чисел и т. д.
Более точное совпадение, как показано в ответе @ chux, или просто:
"(%3d%2d%2d%c, %3d%2d%2d%c) (%3d%2d%2d%c, %3d%2d%2d%c"
(отличается только отсутствием дополнительного пробела и не считывает количество использованных символов - также обратите внимание на закрытие ")"
не требуется в строке формата, когда вы читаете последний символ, например, 'D'
завершает преобразование)
Когда вы используете двумерный массив из 1 строки, в следующем упрощенном примере используется массив 1D для chars
и nums
, и его можно записать следующим образом: fgets()
, передавая буфер в sscanf()
, проверяя возвращаемый результат и выводя собранные значения или отображение ошибки в случае сбоя анализа:
#include <stdio.h>
#define MAXC 1024 /* if you need a constant, #define one (or more) */
int main (int argc, char **argv) {
char buf[MAXC], chars[4];
int nums[12];
/* use filename provided as 1st argument (stdin by default) */
FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;
if (!fp) { /* validate file open for reading */
perror ("file open failed");
return 1;
}
while (fgets (buf, MAXC, fp)) { /* read line into buf with fgets() */
/* parse with sscanf -- validate 16 conversions take place */
if (sscanf (buf, "(%3d%2d%2d%c, %3d%2d%2d%c) (%3d%2d%2d%c, %3d%2d%2d%c",
&nums[0], &nums[1], &nums[2], &chars[0],
&nums[3], &nums[4], &nums[5], &chars[1],
&nums[6], &nums[7], &nums[8], &chars[2],
&nums[9], &nums[10], &nums[11], &chars[3]) == 16) {
/* output result */
printf ("%d %d %2d %c\n%d %d %2d %c\n%d %d %2d %c\n%d %d %2d %c\n",
nums[0], nums[1], nums[2], chars[0],
nums[3], nums[4], nums[5], chars[1],
nums[6], nums[7], nums[8], chars[2],
nums[9], nums[10], nums[11], chars[3]);
} /* or handle error */
else
fprintf (stderr, "error parsing data from: %s\n", buf);
}
if (fp != stdin) /* close file if not stdin */
fclose (fp);
}
Пример входного файла
$ cat dat/splitintoarr.txt
(1231212A, 1231212B) (1231212C, 321128D)
Пример использования / Вывод
$ ./bin/splitintoarr <dat/splitintoarr.txt
123 12 12 A
123 12 12 B
123 12 12 C
321 12 8 D
(выходные данные последнего числа были выведены с использованием модификатора field-width , чтобы обеспечить выравнивание столбцов для ваших данных)
Просмотрите все ответы и дайте нам знать, если у вас есть дополнительные вопросы.