Самое важное для вас сообщение:
Никогда не используйте gets
- оно не может защитить от переполнения буфера. Ваш буфер может содержать 9 символов и символ завершения, но gets
позволит пользователю вводить больше символов и тем самым перезаписывать другие части памяти программ. Злоумышленники могут использовать это. Так что нет gets
в любой программе.
Вместо этого используйте fgets
!
Тем не менее, что для вас не так?
scanf
оставляет новую строку ( aka a '\n'
) во входном потоке. Поэтому первый gets
просто читает пустую строку. А второй gets
затем читает «сурья».
Проверьте это так:
#include <stdio.h>
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
char a[10],b[10];
puts("enter");
gets(a); // !!! Use fgets instead
puts("enter");
gets(b); // !!! Use fgets instead
puts("enter");
printf("|%s| %zu", a, strlen(a));
printf("|%s| %zu", b, strlen(b));
}
return 0;
}
Ввод:
1
surya
whatever
Вывод:
enter
enter
enter
|| 0|surya| 5
Итак, вы видите, что a
- это просто пустая строка (длина ноль) и что b
содержит слово «сурья» (длина 5).
Если вы используете fgets
, вы может защитить себя от инициированного пользователем переполнения буфера - и это важно.
Но fgets
будет , а не удалит '\n'
, оставшийся от scanf
. Вам все равно придется избавиться от этого самого себя.
Для этого я рекомендую также сбросить scanf
. Используйте fgets
, а затем sscanf
. Например:
if (fgets(a,sizeof a, stdin) == NULL)
{
// Error
exit(1);
}
if (sscanf(a, "%d", &t) != 1)
{
// Error
exit(1);
}
Таким образом, приведенный выше код автоматически удалит '\n'
из входного потока при вводе t
, а последующее fgets
начнется со следующего слова.
Установка все вместе:
#include <stdio.h>
int main()
{
int t;
char a[10],b[10];
if (fgets(a,sizeof a, stdin) == NULL)
{
// Error
exit(1);
}
if (sscanf(a, "%d", &t) != 1)
{
// Error
exit(1);
}
while(t--)
{
puts("enter");
if (fgets(a,sizeof a, stdin) == NULL)
{
// Error
exit(1);
}
puts("enter");
if (fgets(b,sizeof b, stdin) == NULL)
{
// Error
exit(1);
}
puts("enter");
printf("%s", a);
printf("%s", b);
}
return 0;
}
Ввод:
1
surya
whatever
Ввод:
enter
enter
enter
surya
whatever
Конечная нота:
fgets
будет - в отличие от gets
- также сохранить '\n'
в буфер назначения. В зависимости от того, что вы хотите сделать, вам, возможно, придется удалить это '\n'
из буфера.