Согласно documentation для зсапЕ (акцент мой):
Строка формата состоит из пробельных символов (любой одиночный символ пробела в строке формата потребляет все доступные последовательные символы пробела из ввода), небелые многобайтовые символы, кроме %
(каждый такой символ в строке формата потребляет ровно один идентичный символ из e) и спецификации преобразования.
Таким образом, ваш формат строки %[^\n]\n
будет первым читать (и магазин) произвольное количество не пробельных символов из входного (из-за %[^\n]
части), а затем, из-за следующей строки, читать (и отбросить) произвольное количество пробельных символов, таких как пробелы, вкладки или символы новой строки.
Таким образом, чтобы сделать ваш зсапЕ остановки чтения ввода, вам необходимо либо ввести по крайней мере один непробельный характер после того, как символ новой строки, или же организовать входной поток до конца (например, нажав Ctrl + D в системах Unix-ish).
Вместо этого, чтобы ваш код работал так, как вы ожидаете, просто удалите последний \n
с конца строки вашего формата (как уже было предложено Umamahesh P).
Конечно, это оставит новую строку еще во входном потоке. Чтобы избавиться от него (в случае, если вы хотите прочитать другую строку позже), вы можете отключить его от потока или просто добавить %*c
(что означает «прочитать один символ и отбросить его») или даже %*1[\n]
(прочитайте одну новую строку и отбросьте это) до конца строки формата scanf.
Ps. Обратите внимание, что в вашем коде есть еще несколько проблем. Например, чтобы избежать ошибок переполнения буфера, вы действительно должны использовать %63[^\n]
вместо %[^\n]
, чтобы ограничить количество символов scanf, которые будут прочитаны в вашем буфере. (Предел должен быть на один меньше размера вашего буфера, так как scanf всегда будет добавлять конечный нулевой символ.)
Кроме того, спецификатор формата %[
всегда ожидает по крайней мере одного совпадающего символа и не будет работать, если ни один из них не будет доступный. Таким образом, если вы сразу нажмете Enter, не набрав ничего, ваш scanf завершится неудачно (тихо, так как вы не проверите возвращаемое значение) и оставит буфер ввода заполненным случайным мусором. Чтобы этого избежать, вы должны a) проверить возвращаемое значение scanf, b) установить input[0] = '\0'
перед вызовом scanf или c) предпочтительно оба.
Наконец, обратите внимание, что если вы просто хотите прочитать ввод строки за строкой, это много проще всего использовать fgets. Да, вам нужно будет лишить конечный символ новой строки (если таковой имеется), если вы этого не хотите, но все же намного проще и безопаснее пытаться использовать scanf для задания, которое на самом деле не предназначено для:
#include <stdio.h>
#include <string.h>
void chomp(char *string) {
int len = strlen(string);
if (len > 0 && string[len-1] == '\n') string[len-1] = '\0';
}
int main(void)
{
char input[64];
printf("Enter some input: ");
fgets(input, sizeof(input), stdin);
chomp(input);
printf("You entered \"%s\".\n", input);
}
Не размещайте изображения текста! – Olaf
его% [^ \ n], попробуйте это –
@ user3121023 Спасибо, именно поэтому я хотел использовать ''% [^ \ n] \ n ". – ivan