Как прочитать неограниченное количество символов в переменной char*
без указания размера?
Например, скажем, я хочу прочитать адрес сотрудника, который также может занимать несколько строк.
Как прочитать неограниченное количество символов в переменной char*
без указания размера?
Например, скажем, я хочу прочитать адрес сотрудника, который также может занимать несколько строк.
Вы должны начать с «угадывания» ожидаемого размера, а затем выделить такой большой буфер, используя malloc
. Если это окажется слишком маленьким, вы используете realloc
, чтобы изменить размер буфера, чтобы он стал немного больше. Образец кода:
char *buffer;
size_t num_read;
size_t buffer_size;
buffer_size = 100;
buffer = malloc(buffer_size);
num_read = 0;
while (!finished_reading()) {
char c = getchar();
if (num_read >= buffer_size) {
char *new_buffer;
buffer_size *= 2; // try a buffer that's twice as big as before
new_buffer = realloc(buffer, buffer_size);
if (new_buffer == NULL) {
free(buffer);
/* Abort - out of memory */
}
buffer = new_buffer;
}
buffer[num_read] = c;
num_read++;
}
Это только что пришло мне в голову и может (читай: вероятно, будет) содержать ошибки, но должно дать вам хорошее представление.
x = realloc(x, newsize);
Если realloc не работает, вы теряете исходный указатель и происходит утечка памяти. Тем не менее, одно исключение из этого правила — это нормально, если ваша политика при сбое выделения ресурсов заключается в завершении процесса.
- person R Samuel Klatchko; 24.03.2010
void *sav=ptr; if((ptr=realloc(ptr,newsiz))==null) { free(sav); }
- person Lawrence Dol; 24.03.2010
realloc(buffer, num_read);
, чтобы обрезать выделенный буфер до точного требуемого размера.
- person caf; 24.03.2010
Abort - out of memory
должно быть return error code
.
- person Gabe; 24.03.2010
new_buffer
находится в начале составного оператора, поэтому оно полностью переносимо на все версии стандартного C.
- person caf; 25.03.2010
strlen()
для этой цели, вам нужно использовать переменную для отслеживания текущего выделенного размера (например, buffer_size
в этом ответе).
- person caf; 25.03.2010
Просто должен был ответить Ex7.1, стр. 330 из Beginning C, Ivor Horton, 3-е издание. Потратил пару недель на отработку. Позволяет вводить числа с плавающей запятой без указания заранее, сколько чисел введет пользователь. Сохраняет числа в динамическом массиве, а затем распечатывает числа и среднее значение. Использование Code::Blocks с Ubuntu 11.04. Надеюсь, поможет.
/*realloc_for_averaging_value_of_floats_fri14Sept2012_16:30 */
#include <stdio.h>
#include <stdlib.h>
#define TRUE 1
int main(int argc, char ** argv[])
{
float input = 0;
int count=0, n = 0;
float *numbers = NULL;
float *more_numbers;
float sum = 0.0;
while (TRUE)
{
do
{
printf("Enter an floating point value (0 to end): ");
scanf("%f", &input);
count++;
more_numbers = (float*) realloc(numbers, count * sizeof(float));
if ( more_numbers != NULL )
{
numbers = more_numbers;
numbers[count - 1] = input;
}
else
{
free(numbers);
puts("Error (re)allocating memory");
exit(TRUE);
}
} while ( input != 0 );
printf("Numbers entered: ");
while( n < count )
{
printf("%f ", numbers[n]); /* n is always less than count.*/
n++;
}
/*need n++ otherwise loops forever*/
n = 0;
while( n < count )
{
sum += numbers[n]; /*Add numbers together*/
n++;
}
/* Divide sum / count = average.*/
printf("\n Average of floats = %f \n", sum / (count - 1));
}
return 0;
}
/* Success Fri Sept 14 13:29 . That was hard work.*/
/* Always looks simple when working.*/
/* Next step is to use a function to work out the average.*/
/*Anonymous on July 04, 2012*/
/* http://www.careercup.com/question?id=14193663 */
Как насчет того, чтобы просто поместить в стек буфер размером 1 КБ (или 4 КБ), считывая его, пока не найдете конец адреса, а затем выделить буфер нужного размера и скопировать в него данные? Как только вы возвращаетесь из функции, буфер стека исчезает, и у вас есть только один вызов malloc
.
fgets
имеет параметр размера буфера. В стандартной библиотеке C определенно есть функции, которых следует избегать (например, gets
). Использование функций с ограниченной длиной и буферов фиксированного размера кажется мне довольно безопасным.
- person tomlogic; 25.03.2010
getline
. - person dmckee --- ex-moderator kitten   schedule 24.03.2010