Диагноз
В коде есть (как минимум) две проблемы:
Вы не предоставили никакого полезного места для хранения строки. (Исходный вопрос определен: char a[] = "";
, который, следует отметить, представляет собой массив длины 1, хотя он может содержать только строку длины 0.)
Вы не сказали scanf_s()
, насколько велика строка. Требуется аргумент длины после указателя на строку символов.
Определение Microsoft для scanf_s()
указывает:
В отличие от scanf
и wscanf
, scanf_s
и wscanf_s
требуют указания размера буфера для всех входных параметров типа c
, C
, s
, S
или наборов строковых элементов управления, заключенных в []
. Размер буфера в символах передается как дополнительный параметр сразу после указателя на буфер или переменную. Например, если вы читаете строку, размер буфера для этой строки передается следующим образом:
char s[10];
scanf_s("%9s", s, _countof(s)); // buffer size is 10, width specification is 9
Размер буфера включает завершающий нуль. Вы можете использовать поле спецификации ширины, чтобы убедиться, что считываемый токен помещается в буфер. Если поле спецификации ширины не используется, а прочитанная лексема слишком велика для размещения в буфере, в этот буфер ничего не записывается.
Примечание
Параметр размера имеет тип unsigned
, а не size_t
.
Оператор _countof()
является расширением Microsoft. Это примерно эквивалентно sizeof(s) / sizeof(s[0])
, что в данном случае совпадает с sizeof(s)
, поскольку sizeof(char) == 1
по определению.
Обратите внимание, что параметр размера равен unsigned
, а не size_t
, как можно было бы ожидать. Это одно из различий между реализацией Microsoft TR 24731-1 функции и Приложение K стандарта ISO/IEC 9899:2011. Размер, указанный в стандарте, технически равен rsize_t
, но он определяется как size_t
с ограниченным диапазоном (отсюда и r
):
Тип rsize_t
, который является типом size_t
.
но сноска (не показана) относится к определению RSIZE_MAX
.
См. также Используете ли вы "безопасные" функции TR 24731?
Исправление кода в вопросе
Пример в цитате от Microsoft во многом показывает, как исправить свой код. Тебе нужно:
int main(void)
{
char a[4096];
printf("Enter word:\n");
if (scanf_s("%s", a, (unsigned)sizeof(a)) != 1) // Note cast!
fprintf(stderr, "scanf_s() failed\n");
else
printf("scanf_s() read: <<%s>>\n", a);
return 0;
}
Обратите внимание, что я проверил результат scanf_s()
, а не просто предположил, что он работает, и сообщил об ошибках стандартной ошибки.
person
Jonathan Leffler
schedule
03.05.2015
char a[50] = {0};
возможно? - person David C. Rankin   schedule 03.05.201520
- person Eugene Sh.   schedule 03.05.2015scanf_s
? Вы имели в видуscanf
правильно? - person David C. Rankin   schedule 03.05.2015scanf_s
вариант - person Eugene Sh.   schedule 03.05.2015scanf_s
является частью приложения K документа C11, но предоставляется только несколькими разработчиками не MS реализация - person Mgetz   schedule 03.05.2015