fstream seekg(), seekp(), et d'écrire()

je cherche des clarifications sur la façon dont seekg() et seekp() des travaux lors de l'écriture dans un fichier. Par exemple, j'avais un fichier comme ça:

offset 0: 2
offset 4: 4
offset 8: 6
offset 12: 8
offset 16: 10

maintenant je veux ouvrir le fichier et faire quelques recherches pour lire et écrire des valeurs.

fstream file;
file.open("file.txt", fstream::in |fstream::out | fstream::binary);
file.seekp(0, ios::end) // seek to the end of the file
int eofOffset = file.tellp(); // store the offset of the end-of-file, in this case 20

int key = 0;

file.seekg(12, ios::beg); // set the seek cursor to offset 12 from the beginning of the file
file.read((char *) &key, (int)sizeof(int)); // read in the next 4 bytes and assign it to key, in this case 8
file.seekg(8, ios::beg); // set the seek cursor to offset 8 from the beginning of the file
file.read((char *) &key, (int)sizeof(int)); // read in the next 4 bytes and assign it to key, in this case 6

Maintenant, je veux écrire à la fin du fichier. Depuis l' seekg() la fonction déplace seulement le curseur de recherche, mon seekp() le curseur doit toujours être à la fin du fichier n'est-ce pas? Donc:

int newKey = 12;
file.write((char *) &newKey, sizeof(int));

devrait maintenant faire ressembler mon fichier à:

offset 0: 2
offset 4: 4
offset 8: 6
offset 12: 8
offset 16: 10
offset 20: 12

maintenant, qu'arrive-t-il à mon fichier si je choisis de chercher un offset et d'écrire sa valeur comme offset à la valeur qui vient d'être insérée. Par exemple, je veux offset 8 tenir eofOffset = 20 puisque nous venons d'insérer 12 à cet offset.

Si je fais:

file.seekp(8, ios::beg);
file.write((char *) &eofOffset, sizeof(int));

est-il correctement réécrire mon fichier ressemble à ceci:

offset 0: 2
offset 4: 4
offset 8: 20
offset 12: 8
offset 16: 10
offset 20: 12

s'il vous Plaît laissez-moi savoir si je suis en train de tout les erreurs à l'aide de la seekg() et seekp() fonctions.

21
demandé sur raphnguyen 2013-03-28 02:01:19

1 réponses

le modèle de classe std::basic_filebuf occupe une position de fichier unique

  1. la classe basic_filebuf associe les deux entrées séquence et séquence de sortie avec un fichier.
  2. Les restrictions sur la lecture et l'écriture d'une séquence contrôlée par un objet de la classe basic_filebuf sont les mêmes que pour lecture et écriture avec les fichiers de bibliothèque C Standard.
  3. En particulier:
    • Si le fichier n'est pas ouvert pour la lecture de la séquence d'entrée ne peut pas être lu.
    • si le fichier n'est pas ouvert pour l'écriture, la séquence de sortie ne peut pas être écrite.
    • une position de fichier commune est maintenue pour la séquence d'entrée et la séquence de sortie.

ce Que cela signifie est que lorsque vous utilisez un std::basic_fstream, qui par défaut utilise un std::basic_filebuf, la position du fichier unique est déplacée par les deux seekp() et seekg(); à moins que vous utilisez une variable séparée pour stocker une des positions de sorte que vous pouvez ensuite chercher à nouveau à elle, vous ne pouvez pas garder la trace de put et obtenir des positions indépendamment.

les implications du point 2 sont qu'entre lit et écrit sur un fstream vous devez soit rincer le tampon ou chercher la position du fichier lors du passage de la sortie à l'entrée, et vous devez soit être à la fin du fichier ou chercher la position du fichier lors du passage de l'entrée à la sortie.

Pour plus de détail sur ces restrictions, voir la section 7.19.5.3 / 7 de la norme C99 ("the fopen fonction"), ou 7.21.5.3/7 de C11.

22
répondu user657267 2016-09-02 06:28:44