Ecrire sur une position donnée
Discutez d'informatique ici !
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 13:21
Je voudrais arriver à écrire dans un fichier sur une position donné.
J'ai vu les fonctions fread et fwrite; mais trop tard j'ai déjà commencé mon travail avec des fprintf et fscanf
Je me demandais donc si ceci pouvait marcher
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
uchar block;
fseek(disk_id,BLOCK_SIZE,pos); /*on se place à la position pos dans le fichier*/
fscanf(disk_id,"%hhu",block); /*on stocke dans block la chaine de BLOCK_SIZE uchar ???? */
}
}
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 13:46
Bonjour,
Si les choses sont bien faites normalement cela ne devrait pas poser de problème.
Mais il faut que tu testes pour vérifier que cela fonctionne. Il te suffit de faire un fprintf sur block pour vérifier que cela concorde bien.
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 13:50
Nop; j'ai fait des tests et ça a planté ça n'affiche pas ce qu'il faut, je suis en train de voir pour essayer de passer tout avec write et read...
En revanche ça ne fonctionne pas comme ça devrait
char tab[]="coucou";
fwrite( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
fread( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
fwrite écrit bien dans mon fichier, mais fread ne m'affiche rien; erreur de ma part ?
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 13:52
Lorsque tu fais un fscanf, il va jusqu'à la fin de la ligne, donc il faut être sûr que tu n'ais qu'un seul paramètre dans ta chaine.
Malgré tout je pense qu'une solution avec read / write est plus simple et plus préférable que l'utilisation d'un fscanf.
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:02
ampholyte a écrit:Lorsque tu fais un fscanf, il va jusqu'à la fin de la ligne, donc il faut être sûr que tu n'ais qu'un seul paramètre dans ta chaine.
Malgré tout je pense qu'une solution avec read / write est plus simple et plus préférable que l'utilisation d'un fscanf.
Désolé, j'ai édité le dernier post avant que tu n'écrives

Deux soucis; que je fasse
fwrite( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
ou un fseek avant; j'écris dans les deux cas au début du fichiers (que j'ouvre en r+)
et le freed n'affiche rien.
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
joel76
- Membre Relatif
- Messages: 230
- Enregistré le: 11 Fév 2013, 15:31
-
par joel76 » 07 Jan 2014, 14:08
Le fscanf ne peut-être utilisé que pour lire du texte.
Si on fait un fwrite, il faut absolument faire un fread sinon c'est de la mauvaise conception de programme.
De tout façon, après le fwrite il faut faire un fflush(disk_id) pour forcer l'écriture sur le disque (apparemment pas obligatoire, je viens de tester chez moi), et revenir à la position où on a écrit avec un fseek pour pouvoir lire correctement ce qui a été écrit.
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 14:09
Peux-tu mettre ton code contenant l'écriture et la lecture également avec ton fseek complet ? Après ton fwrite tu dois remettre le curseur de ton flux au début de ton fichier.
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:12
Bien; alors la séquence suivante; n'affiche rien du tout
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
fseek(disk_id,BLOCK_SIZE,pos);
char tab[]="coucou";
fwrite( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
fseek(disk_id,BLOCK_SIZE,pos);
fread( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
}
}
Main
- Code: Tout sélectionner
FILE *source;
source = fopen("test.txt", "r+" );
read_block(5,source);
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
joel76
- Membre Relatif
- Messages: 230
- Enregistré le: 11 Fév 2013, 15:31
-
par joel76 » 07 Jan 2014, 14:16
Ceci fonctionne chez moi :
- Code: Tout sélectionner
int main()
{
char tab[]="coucou";
char tab1[1024];
size_t nb;
FILE *f = fopen("C:\\a-travail\\developpements\\Visual Studio\\C\\test_fseek\\test.txt", "wb+");
fwrite( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , f);
fseek(f, -sizeof(tab)/sizeof(tab[0]), SEEK_CUR) ;
nb = fread( tab1 , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , f);
fclose(f);
tab1[nb] = 0;
puts(tab1) ;
_getch();
return 0;
}
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 14:21
En modifiant rapidement ton code, ceci fonctionne chez moi :
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
char tab[]="coucou";
fseek(disk_id,pos,SEEK_SET);
fwrite( tab , sizeof(tab[0]), strlen(tab), disk_id);
fseek(disk_id, pos, SEEK_SET);
fread( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
fprintf(stderr, "%s\n", tab);
}
}
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:23
ampholyte a écrit:En modifiant rapidement ton code, ceci fonctionne chez moi :
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
char tab[]="coucou";
fseek(disk_id,pos,SEEK_SET);
fwrite( tab , sizeof(tab[0]), sizeof(tab)/sizeof(tab[0]), disk_id);
fseek(disk_id, pos, SEEK_SET);
fread( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id);
fprintf(stderr, "%s\n", tab);
}
}
Oui mais là tu te sers de SEEK_SET et non de la position en paramètres !!!
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 14:24
Et bien si ma position correspond à mon offset à partir du début.
- Code: Tout sélectionner
fseek(disk_id,pos,SEEK_SET);
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:29
Ce que je veux dire avec ça; tu vas avancer de pos octets à partir de la position courante SEEK_SET
Moi je veux avancer de BLOCK_SIZE octet à partir de la position pos ;)
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 14:31
D'accord utilise alors la technique de joel76 c'est à dire de faire un fseek négatif après ton fwrite.
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:40
Toujours pas
Du mieux je prend bien le décalage et j'écris au bon endroit au début, en revanche je n'ai toujours pas l'affichage de read
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
fseek(disk_id,BLOCK_SIZE,pos);
char tab[]="coucou";
fwrite( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id); // ==> OK
fseek(disk_id,-BLOCK_SIZE,SEEK_CUR);
fread( tab , sizeof(tab[0]) , sizeof(tab)/sizeof(tab[0]) , disk_id); // aucun affichage
}
}
Y a t'il un moyen de faire une sorte de code de retour sur fread pour voir si la lecture se fait ?
EDIT; pur l'écriture j'ai parlé trop vite, ça marche pour pos=1 et pos=2 ça me mettre respectivemment 4 et 8 espace; mais pour pos=3 ça me récrit au début du fichier.
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
joel76
- Membre Relatif
- Messages: 230
- Enregistré le: 11 Fév 2013, 15:31
-
par joel76 » 07 Jan 2014, 14:43
Euh, tu fais bien un puts de tab, non ?
Teste les retour de fseek, si c'est -1 il y a un problème.
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 14:46
Est-ce que tu fais bien un printf de tab après ton fread ?
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 14:53
En rajoutant puts(tab) il m'écrit cou sans les espaces qui sont censées être devant
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
Rockleader
- Habitué(e)
- Messages: 2126
- Enregistré le: 11 Oct 2011, 18:42
-
par Rockleader » 07 Jan 2014, 15:21
J'ai fini par le faire fonctionner au sein d'une même fonction;
maintenant j'aimerais arriver à séparer tout ça; une fonction permettant d'écrire et une d'afficher
- Code: Tout sélectionner
void write_blocks(int pos,FILE* disk_id)
{
fseek(disk_id,BLOCK_SIZE,pos);
char block[BLOCK_SIZE]={0};
printf("Quel block voulez vous entrer:");
scanf("%s",block);
fwrite( block , sizeof(block[0]) , sizeof(block)/sizeof(block[0]) , disk_id);
}
- Code: Tout sélectionner
void read_block(int pos,FILE* disk_id)
{
if (disk_id != NULL)
{
char block[BLOCK_SIZE]={0};
fseek(disk_id,BLOCK_SIZE,pos);
fread( block , sizeof(block[0]) , sizeof(block)/sizeof(block[0]) , disk_id);
puts(block);
}
}
Sa compile mais je suis pas sur d'employer la bonne méthodes; les valeurs sont en fait stocké dans block par fread puis affiché par puts ?
Cette histoire est entièrement vraie puisque je l'ai inventé du début à la fin !
-
ampholyte
- Membre Transcendant
- Messages: 3940
- Enregistré le: 21 Juil 2012, 07:03
-
par ampholyte » 07 Jan 2014, 15:37
Rockleader a écrit:Sa compile mais je suis pas sur d'employer la bonne méthodes; les valeurs sont en fait stocké dans block par fread puis affiché par puts ?
Tout à fait, la fonction puts est équivalente à
- Code: Tout sélectionner
fprintf(stdout,"%s\n", ma_chaine)
Utilisateurs parcourant ce forum : Aucun utilisateur enregistré et 9 invités