Как говорит Сурав, вам необходимо использовать strtok
для токенизирующих строк. Но это не объясняет , почему ваш существующий код не работает.
Ответ лежит в спецификации для sscanf
и как он обрабатывает код '%s'
в строке формата.
С man
страницы:
s Соответствует последовательности без пробельных символов;
Таким образом, наличие пробела в строке форматирования в значительной степени не имеет отношения к математике первого '%s'
. Когда sscanf
видит первый номер , он просто потребляет входную строку до тех пор, пока не встретится символ пробела, предоставив вам ваше значение для name
из "file1.h:"
(обратите внимание на включение двоеточия).
Затем он пытается разобраться с последовательностью пробелов в строке форматирования.
Опять же, из man
страницы
Строка формата состоит из последовательности директив, которые описывают, как обрабатывать последовательность входных символов.
Последовательность двоеточия пробела не соответствует какой-либо известной директиве (т. Е. «%», За которой следует что-то), и таким образом вы получите соответствующий сбой.
Если вместо этого ваша строка формата была просто "%s%s"
, тогда sscanf
доставит вам почти то, что вы хотите.
int main(int argc, char *argv[]) {
char str[] = "file1.h: file2.c,file3.cpp";
char name[100];
char depends[100];
sscanf(str, "%s%s", name, depends);
printf("str: '%s'\n", str);
printf("Name: %s\n", name);
printf("Deps: %s\n", depends);
return 0;
}
Что дает этот вывод:
str: 'file1.h: file2.c,file3.cpp'
Name: file1.h:
Deps: file2.c,file3.cpp
На данный момент, вы можете просто проверить, что sscanf
дал возвращаемое значение 2 (т.е. он нашел два значения), и что последний символ name
это двоеточие. Затем просто усекайте name
, и у вас есть свой ответ.
Конечно, по этой логике, вы не собираетесь быть в состоянии использовать sscanf
разобрать вашу depends
переменную в несколько строк ... поэтому другие рекомендуют с помощью strtok
, strpbrk
и т.д., потому что вы оба синтаксического анализа и токенизируя ваш вход.
Возможно, вы захотите проверить возвращаемое значение 'sscanf()' и считать, что ''% s '' * really * не соответствует '':'', как вы, кажется, предполагаете. – EOF
': и backspace' .. вы уверены? –
, если это ':' и '' (пробел), почему бы вам не попробовать 'strtok()'? он принимает больше, чем когда-то разграничитель, FWIW. –