2016-11-04 4 views
0

Я хочу прочитать некоторый строковый ввод от пользователя и записать его в файл. Сейчас я делаюC - сохранение пользовательского ввода в динамическом массиве символов?

char name[25]; 
scanf("%s", name); 
int handle = open("./visitors.txt", O_RDWR|O_CREAT, S_IRUSR|S_IWUSR); 
if (handle < 0){ 
    printf("File error.\n"); 
    return; 
} 
lseek(handle, -sizeof(name), SEEK_END); 
write(handle, name, sizeof(name)); 

Это, конечно, не прав, так как большую часть времени пользователь не запишет 25 символов, только меньше, поэтому, когда пользователь вводит 5 символов, остальные 20 будут быть пустым, и в итоге у меня есть 5 символов, которые пользователь вложил, и 20 таблеток в моем выходном файле. Как я могу убедиться, что в файл записывается только пользовательский ввод?

+0

Читая руководство по эксплуатации 'scanf'? '% s' приводит к завершению вывода. –

+0

'-sizeof (name)' должно быть '- (off_t) sizeof (name)' –

+0

@ M.M Не имеет значения. –

ответ

1

Используется необработанные системные вызовы для обработки файловых операций. Если ваше намерение специально не узнать о системных вызовах, вы не должны этого делать. The write call записывает несколько байтов, заданных третьим параметром. sizeof(name) ошибочно в этом случае. Он будет не возвращает длину строки, она вернет длину всего буфера.

Стандарт strlen function дает вам длину строки. Таким образом, запуск strlen(name) даст вам 5, если пользователь вводит 5 символов, в отличие от sizeof, которые вы используете.

Если вы не хотите, чтобы узнать о системных вызовов в частности, вы, вероятно, следует обрабатывать операции с файлами со стандартной библиотекой C, используя fprintf для вывода в файл, и такие функции, как fopen и fclose. Посмотрите at the fprintf docs, которые также ссылаются на другие функции.

+0

Вот и все! Использование 'strlen()' вместо 'sizeof()' исправлено. Спасибо! –

1

Я не уверен, почему вы хотите использовать системные вызовы низкого уровня open, lseek, write. Обычно гораздо удобнее использовать стандартные функции для таких задач, как стандартные функции C fopen, fscanf, fprintf.

В этом случае, вы можете попробовать fgets, чтобы получить строку ввода из stdin, а затем использовать fprintf с %s записать в файл. Вы все равно можете использовать буфер name[25] или name[100] (envision для наибольшего входа от stdin). Просто инициализируйте его правильно, чтобы убедиться, что он завершен NULL. Тогда fprintf с %s будет правильно писать строку (т. Е. Без окончания талисмана) в файл.

+0

Как я могу убедиться, что буфер завершен нулем? –

+0

Просто инициализируйте его 'char name [25] =" ";' – artm

+0

Если вам нужно использовать 'name' в цикле, тогда' memset' его на все ноль в начале цикла – artm

Смежные вопросы