При чтении ввода из любого файла (включая стандартный ввод), где вы не знаете длину, часто лучше использовать getline
, а не scanf
или fgets
, потому что getline
будет обрабатывать выделение памяти для вашей строкиавтоматически, если вы предоставляете нулевой указатель для получения введенной строки.Этот пример иллюстрирует:
#include <stdio.h>
#include <stdlib.h>
int main (int argc, char *argv[]) {
char *line = NULL; /* forces getline to allocate with malloc */
size_t len = 0; /* ignored when line = NULL */
ssize_t read;
printf ("\nEnter string below [ctrl + d] to quit\n");
while ((read = getline(&line, &len, stdin)) != -1) {
if (read > 0)
printf ("\n read %zd chars from stdin, allocated %zd bytes for line : %s\n", read, len, line);
printf ("Enter string below [ctrl + d] to quit\n");
}
free (line); /* free memory allocated by getline */
return 0;
}
Соответствующие части:
char *line = NULL; /* forces getline to allocate with malloc */
size_t len = 0; /* ignored when line = NULL */
/* snip */
read = getline (&line, &len, stdin);
Установка line
в NULL
заставляет getline автоматически выделять память.Пример вывода:
$ ./getline_example
Enter string below [ctrl + d] to quit
A short string to test getline!
read 32 chars from stdin, allocated 120 bytes for line : A short string to test getline!
Enter string below [ctrl + d] to quit
A little bit longer string to show that getline will allocated again without resetting line = NULL
read 99 chars from stdin, allocated 120 bytes for line : A little bit longer string to show that getline will allocated again without resetting line = NULL
Enter string below [ctrl + d] to quit
Так что с getline
вам не нужно угадывать, какова будет длина строки вашего пользователя.