2015-06-01 4 views
-4

Мне нужно открыть файл, содержащий каждое число в новой строке. (представлен как строка)
Для чтения данных мне нужно использовать getline().
Чтобы изменить данные из строки в int, мне нужно использовать atoi().
Чтобы записать измененные данные в файл, мне нужно использовать write().

Что мне удалось сделать это:Запись int в двоичный файл в C

#include <stdlib.h> 
#include <string.h> 
#include <fcntl.h> 
#include <unistd.h> 
#include <sys/types.h> 

int main() 
{ 
    FILE *stream; 
    stream = fopen("stevila.txt", "r"); 

    FILE *fd = fopen("test.bin", "w+"); 

    char *line = NULL; 
    size_t len = 0; 
    ssize_t read; 
    int a=10; 
    char str[8192]; 


    while ((read = getline(&line, &len, stream)) != -1) { 
     strcpy(str, line); 
     int val = atoi(str); 
     write(fd, val, a); 
    } 

    free(line); 
    fclose(stream); 
} 

EDIT:
Благодаря ответам, мне удалось создать программу, которая работает:

#include <stdio.h> 
#include <stdlib.h> 
#include <fcntl.h> 
#include <unistd.h> 

int main() 
{ 
    FILE *f = fopen("text.txt","r"); 

    mode_t mode = S_IRUSR | S_IWUSR; /* Allow user to Read/Write file */ 
    int fd = open("out.bin",O_WRONLY|O_CREAT|O_TRUNC,mode); 

    if (f==NULL) { 
     perror("Error while opening 'text.txt' "); 
     return -1; 
    } 
    if(fd < 0){ 
     perror("Error while opening 'out.bin' "); 
     return -1; 
    } 

    size_t max_size=64; 
    char* line; 
    line=malloc(max_size); 

    int d; 
    while ((d=getline(&line, &max_size, f))!=-1) 
    { 
     int tmp=atoi(line); /* Change string to int and save it to tmp */ 
     if(write(fd,&tmp,sizeof(tmp)) == -1) 
     { 
      perror("Error while writing data "); 
      break; 
     } 
    } 

    fclose(f); 
    close(fd); 
    free(line); 

    return 0; 
} 

Теперь мы можем выполните эту команду в терминале, чтобы узнать, соответствует ли выходной файл:

od -i out.bin 
+0

'printf ("% s ", fd);' --- uhhh ... это определенно не то, что вы намереваетесь это сделать. – mah

+0

Это прокомментировано, поэтому он не работает. –

+0

Я редактировал мой код сейчас sry, я его в комментариях, потому что я пытался dfferent вещи – yack

ответ

2

Вы не можете использовать FILE* в качестве аргумента для write. У вас есть следующие варианты:

  1. Использование fwrite. Подпись fwrite является:

    size_t fwrite(const void *buffer, size_t size, size_t count, 
           FILE *stream); 
    
  2. Получить дескриптор файла из FILE* с помощью функции fileno и использовать write. Подпись fileno является:

    int fileno(const FILE *stream); 
    

    подпись write является

    ssize_t write(int fildes, const void *buf, size_t nbyte); 
    

    Использование write не является правильным. Вы передаете val, который не является адресом переменной. Вы используете a в качестве третьего аргумента. Это должно быть изменено на:

    write(fd, &val, sizeof(val)); 
    
  3. Использование open вместо fopen.

Моя рекомендация будет заключаться в использовании fwrite. Это стандартная функция библиотеки C, тогда как write - нет.

Также не забудьте открыть файл в двоичном режиме. Вместо использования "w+" используйте "wb".

FILE *fd = fopen("test.bin", "wb"); 

Добавить строку, чтобы закрыть файл перед выходом. Если вы используете fopen, чтобы открыть файл, используйте fclose, чтобы закрыть его. Если вы используете open, чтобы открыть файл, используйте close, чтобы закрыть его.

+0

Возможно, вы должны включить, что дескриптор файла также должен быть закрыт. – UpAndAdam

+0

@UpAndAdam, хорошая идея. –

+0

Третий вариант: используйте 'open' вместо' fopen'. :) – lurker

2

write принимает дескриптор файла в отличие от указателя файла. На Linux O/S, например.

http://linux.die.net/man/2/write

Почему бы просто не использовать функцию FWRITE, чтобы делать то, что вам нужно

http://www.cplusplus.com/reference/cstdio/fwrite/

Вы можете использовать указатель файла, возвращаемый из fopen с этой функцией и печати по требованию.

+0

'fprintf()' doesn/t выдает двоичные данные, о чем вопрос говорит здесь. 'fwrite()' однако, как это было предложено в комментарии @ EugeneSh. – mah

+0

обновлен. это функция, о которой я думал. спасибо – user3742467