2010-11-11 7 views
6

Par souci d'apprentissage C et comprendre la différence entre les fichiers binaires et des fichiers texte, je tente d'écrire une chaîne de fichier en tant que les deux types de fichiers comme ceci:Pourquoi fwrite() n'écrit pas un fichier binaire en utilisant "wb", en C, sur Mac OS X?

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); 

Toutefois, les deux "wt" et "wb" écrivent en tant que fichier texte, où "wb" doit être écrit en tant que fichier binaire. Hex apparaît comme si pour les deux fichiers:

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

Pourquoi cela se produit, et comment puis-je écrire quelque chose comme un fichier binaire? J'ai lu que le système d'exploitation (Mac OS X 10.6 - GCC 4.2) pourrait ne pas faire la différence entre les fichiers binaires et les fichiers texte, même si je suis toujours perplexe pourquoi un éditeur hexadécimal ne détecterait aucune différence.

+0

Je me demande ce que vous êtes censé voir dans le fichier "binaire"? – Vovanium

Répondre

6

Tous les fichiers sont binaires. La différence entre "fichiers texte" et "fichiers binaires" dans le contexte fopen est que la bibliothèque standard peut utiliser un filtre pour lire et écrire le fichier en mode texte. En mode binaire, ce que vous écrivez est toujours ce qui est écrit. Le seul exemple pratique que je connaisse est dans Windows, où l'ouverture d'un fichier en mode texte le convertira entre les fins de ligne Windows (CRLF, "\r\n") et les fins de ligne de type C/Unix (LF , "\n"). Par exemple, lorsque vous ouvrez un fichier à lire dans Windows en mode texte, les fins de ligne apparaîtront comme "\n" dans votre programme. Si vous deviez l'ouvrir en mode binaire, les fins de ligne apparaîtraient comme "\r\n" dans votre programme.


Vous pouvez également inspecter votre fichier avec cat, par exemple:

chat nom

Vous devriez obtenir la sortie: I am a string!

+0

La syntaxe correcte est "nom de fichier chat". – Darron

+1

Pour clarifier; Les crochets autour de "' filename "" étaient juste destinés à illustrer que c'est une variable, pas quelque chose à copier mot pour mot. Remplacez donc la chaîne '' par le nom de fichier réel, et vous devriez être bon :) –

+4

Les versions de Mac OS antérieures à OS X utilisaient' \ r' pour désigner les fins de ligne, donc la distinction mode texte/mode binaire était pertinents là aussi. – caf

1

Le seul mode de texte de différence fait aux fins de ligne. Donc, si vous fprintf un \n il sera traduit selon la plate-forme. Pour votre exemple, le mode binaire ou texte ne fait aucune différence avec ce qui est écrit dans le fichier.

3

Les deux fichiers sont des fichiers binaires. Ils sont une copie exacte des données que vous avez envoyées à fwrite. Certains systèmes d'exploitation endommagés ont des fichiers texte qui ne sont pas binaires; ils ont des déchets supplémentaires comme \r\n remplaçant \n, ou des enregistrements de ligne de taille fixe, etc. POSIX interdit tout cela. Sur n'importe quel système d'exploitation POSIX, le mode texte et le mode binaire sont identiques. Par ailleurs, "wt" n'est pas un argument valide en mode fopen. Le mode texte est par défaut. Le modificateur t pour demander le mode texte est une extension des implémentations Windows défectueuses où binary est la valeur par défaut mais le mode texte est disponible sur demande.

+0

Quelles implémentations ont binaire comme mode par défaut? Mon expérience a toujours été le mode texte par défaut (et, dans MS C, le modificateur 't' est redondant mais les gens l'utilisent pour plus de clarté) –

+0

@ M.M: Le mode texte est toujours le mode par défaut; Ceci est requis par ISO C. POSIX exige que le mode texte et le mode binaire soient identiques, cela n'a donc aucune importance. –

1

Sur la plupart Unix- comme les systèmes, il y a non différence entre l'ouverture d'un fichier en mode texte et en mode binaire.En outre, les données que vous écrivez ci-dessus ne montreraient pas de différence même sur de nombreux systèmes qui traitent les fichiers "texte" et "binaire" différemment. Par exemple, à l'ouverture de Windows un fichier en mode texte signifie typiquement qu'un "\ n" que vous écrivez sera traduit en "\ r \ n" dans le fichier actuel (et pendant la lecture, le contraire est fait) . Puisque vous n'avez pas écrit «\ n», cette traduction ne se produirait pas.

+0

Remplacer "most" par "all". POSIX requiert que le mode texte et le mode binaire soient identiques. C'est tellement fondamental que je ne pense pas que vous pourriez considérer n'importe quel système d'exploitation qui ne ressemble pas à "Unix-like". –

1

Vous avez raison. Cela n'a pas d'importance sur les systèmes de type Unix. Discussion from the cygwin camp. Quelle différence vous attendiez-vous de voir? Vous écrivez du texte ASCII dans un fichier, et non des données binaires arbitraires.

0

Unix like OS traite les deux comme identiques. Je ne suis pas sûr que ce soit la bonne réponse, mais si vous voulez mettre un texte en hexadécimal dans un fichier, essayez d'appliquer \ x avant le texte.e.g. Si vous essayez d'écrire bonjour dans un fichier, votre tampon sera:
char * buf = "hello";
Si vous voulez écrire hex de "bonjour" dans le fichier, votre tampon devrait être comme ceci
char * buff = "\ x68 \ x65 \ x6c \ x6c \ x6f";
J'espère que cela a aidé

+0

En mémoire, les deux 'buff' sont exactement les mêmes. Il n'y a pas de différence. – Zulan

+0

Oui, mais la différence est lorsque vous l'écrivez dans le fichier. Dans le premier cas "bonjour", il sera écrit en tant que texte dans le fichier, tandis que "\ x68 \ x65 \ x6c \ x6c \ x6f" sera écrit comme hexadécimal dans le fichier pas de texte – fluffybunny

+0

C'est faux. Comme il n'y a pas de différence de mémoire, 'fwrite' écrit simplement un bloc de données identique dans un fichier. Vous devez utiliser '\ x' uniquement pour les caractères qui ne peuvent pas être directement codés dans le fichier source. Essayez-le. – Zulan