Почему fwrite () не записывает двоичный файл с использованием "wb" в C на Mac OS X? - PullRequest
6 голосов
/ 11 ноября 2010

Ради изучения C и понимания разницы между двоичными файлами и текстовыми файлами я пытаюсь записать строку в файл в виде файлов обоих типов, например так:

char * string = "I am a string!";

FILE * filePtrA = fopen("/output.txt", "wt");
fwrite(string, strlen(string), 1, filePtrA);

FILE * filePtrB = fopen("/output.bin", "wb");
fwrite(string, strlen(string), 1, filePtrB);

fclose(filePtrA);
fclose(filePtrB);

Однако оба "wt" и "wb" пишут как текстовый файл, где "wb" должен писать как двоичный файл.Hex выглядит примерно так для обоих файлов:

49 20 61 6D 20 61 20 73 74 72 69 6E 67 21

Почему это происходит, и как я могу записать что-то в виде двоичного файла?

Я прочитал эту ОС (Mac OS X 10.6- GCC 4.2) может не проводить различий между двоичными и текстовыми файлами, хотя я все еще не понимаю, почему шестнадцатеричный редактор не обнаружит никакой разницы.

Ответы [ 6 ]

6 голосов
/ 11 ноября 2010

Все файлы являются двоичными.

Разница между "текстовыми файлами" и "двоичными файлами" в контексте fopen заключается в том, что стандартная библиотека может использовать фильтр для чтения и записи файла в текстовом режиме. В двоичном режиме то, что вы пишете, всегда то, что написано.

Единственный известный мне практический пример - это Windows, где при открытии файла в текстовом режиме он преобразуется между окончаниями строк в стиле Windows (CRLF, "\r\n") и окончаниями строк в стиле C / Unix ( LF, "\n"). Например, когда вы открываете файл для чтения в Windows в текстовом режиме, окончания строк в вашей программе будут выглядеть как "\n". Если бы вы открывали его в двоичном режиме, окончания строк в вашей программе выглядели бы как "\r\n".


Вы также можете проверить файл с помощью cat, например:

кошка имя файла

Вы должны получить вывод: I am a string!

3 голосов
/ 11 ноября 2010

Оба файла являются двоичными файлами. Они являются точной копией данных, которые вы отправили на fwrite. Некоторые сломанные операционные системы имеют текстовые файлы, которые не являются двоичными; у них есть дополнительный мусор, такой как \r\n, заменяющий \n, или записи строк фиксированного размера и т. д. POSIX запрещает все это. В любой операционной системе POSIX текстовый и двоичный режим идентичны.

Кстати, "wt" не является допустимым аргументом режима для fopen. Текстовый режим по умолчанию. Модификатор t для запроса текстового режима является расширением сломанных реализаций Windows, где двоичный файл используется по умолчанию, но текстовый режим доступен по запросу.

1 голос
/ 11 ноября 2010

Ты прав.Это не имеет значения в Unix-подобных системах. Обсуждение из лагеря cygwin .Какую разницу вы ожидали увидеть?Вы пишете текст ASCII в файл, а не произвольные двоичные данные.

1 голос
/ 11 ноября 2010

В большинстве Unix-подобных систем нет разницы между открытием файла в текстовом и двоичном режимах.Кроме того, данные, которые вы пишете выше, не будут иметь разницы даже во многих системах, которые делают по-разному обрабатывают «текстовые» и «двоичные» файлы.

Например, наWindows, открывающий файл в текстовом режиме, обычно означает, что написанная вами «\ n» будет преобразована в «\ r \ n» в реальном файле (и во время чтения выполняется обратное).Поскольку вы не написали "\ n", этот перевод не произойдет.

1 голос
/ 11 ноября 2010

Единственная разница в текстовом режиме - это конец строки.Итак, если вы fprintf a \n, он будет переведен в соответствии с платформой.Для вашего примера бинарный или текстовый режим не имеет значения для того, что записывается в файл.

0 голосов
/ 26 февраля 2016

Unix как OS рассматривает оба как одно и то же.Я не уверен, что это правильный ответ, но если вы хотите поместить текст в виде шестнадцатеричного в файл, попробуйте применить \ x перед text.eg, если вы пытаетесь записать привет в файл, ваш буфер будетbe:
char * buf = "hello";
Если вы хотите записать в файл гекс "hello", ваш буфер должен выглядеть следующим образом:
char * buff = "\ x68 \ x65 \ x6c\ x6c \ x6f ";
Надеюсь, это помогло

...