En espérant que tout va bien pour vous, moi je suis légèrement bloqué sur un TP que j'ai quasiment fini mais à qui il manque encore une fonctionnalité. Alors je vous explique en classe on a abordé les piles et le but du tp était de répresenter les données de piles de trois manières, sur la console, avec des node_t et maintenant en l'affichant sur un fichier .txt.
Le programme doit insérer des valeurs dans le style des piles (LIFO) et doit les dépiler également. J'arrive à tout faire (lecture de fichier, écriture sur le fichier) sauf le dépiler. J'ai essayé de jouer avec les fgetc afin de récupérer le pointeur de la valeur pour chaque ligne mais malheureusement j'échoue. Je sais que je suis très proche du but mais un petit coup de main ne serait pas de refus.
Je vous mets les codes sources pour chaque partie du coup
stack_file.h
#ifndef STACK_FILE_H_INCLUDED
#define STACK_FILE_H_INCLUDED
#define MAX_FLNM 100
typedef struct {
char filename[MAX_FLNM];
int fd; // file descriptor of the open file
int top_off; // final offset
} stack_t;
void set_file(stack_t *); // special function to determine the file to be used
void init_stack(stack_t*); // initalize the data structure
int push_stack(stack_t *, int); // push value into stack
int pop_stack(stack_t *, int *); // pops top value from stack;
int top_stack(stack_t *, int *); // returns top value of stack
void display_stack(stack_t *); // displays the contents of the stack
#endif // STACK_FILE_H_INCLUDED
stack_file.c
#include <stdio.h>"
#include "stack_file.h"
#include <string.h>
void set_file(stack_t *s)
{
FILE* file;
file=fopen("file.txt","w+");
printf("test set \n");
}
void init_stack(stack_t* s)
{
char nom []="file.txt";
strcpy(s->filename,nom);
s->fd=fopen("file.txt", "w+");
s->top_off=0;
printf("test init \n");
} // initalize the data structure
int push_stack(stack_t* s, int val)
{
printf("test push \n");
fseek (s->fd, 0, SEEK_END);
fprintf(s->fd, "%d \n",val);
} // push value into stack
int pop_stack(stack_t* s, int *val)
{
fseek(s->fd,0,SEEK_CUR);
fputs("",s->fd);
*val=fgetc(s->fd);
printf("test pop \n");
}
// pops top value from stack;
//int top_stack(stack_t *, int *); // returns top value of stack
void display_stack(stack_t* s)
{
printf("test display \n");
fopen(s->fd,"r+");
} // displays the contents of the stack
main.c
#include <stdio.h>
#include <stdlib.h>
#include "stack_file.h"
int main() {
stack_t p;
set_file(&p);
init_stack(&p);
push_stack(&p, 5);
push_stack(&p, 6);
push_stack(&p, 7);
display_stack(&p);
scanf("%*c");
int val;
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val); // fails
printf("popped value = %d\n", val); // prints out the old value
display_stack(&p);
}
Du coup la fonction pop_stack renvoie un pointeur sur la valeur qui a été dépilée, le problème c'est que je n'arrive pas à trouver un moyen à avoir accès à cette valeur, mais je sais que ça tourne autour de fseek et de fgetc. Hésitez pas à me donner des conseils sur le code aussi si je fais des choses inutiles, moi de mon côté je continue à chercher les fonctions dans le stdio.h qui pourront m'aider.
Merci à tous ceux qui m'aideront et bonne journée!
Tu dois avoir pas mal de warnings (si pas des erreurs): fopen() renvoie un pointeur (FILE *), pas un descripteur (un int).
Ou tu emploies les fonctions de io.h (open, read, write, close) avec un file descriptor (un int), ou tu emploies celles de stdio.h (fopen, fread, fwrite, fclose) avec un pointeur (FILE *). Parce que, ligne 16 par exemple, fd=fopen(), ça va pas le faire.
- Edité par edgarjacobs 22 septembre 2018 à 13:24:59
On écrit "j'ai tort", pas "tord" qui est le verbe "tordre" à la 3ème personne de l'indicatif présent
Je t'assure que de ce côté j'ai ni warning ni error. La fonction d'écriture arrive à écrire ce qui est demandé, le seul souci que j'ai c'est le pop_stack qui lui j'arrive pas à trouver.
Je t'assure que de ce côté j'ai ni warning ni error
Les options de ton compilateur son mal réglées.
D'abord les erreurs, puis le code compilé (gcc 6.3.0, options -std=c11 -Wall -Wextra):
stack.c: In function 'set_file':
stack.c:26:11: warning: variable 'file' set but not used [-Wunused-but-set-variable]
FILE* file;
^~~~
stack.c:24:24: warning: unused parameter 's' [-Wunused-parameter]
void set_file(stack_t *s)
^
stack.c: In function 'init_stack':
stack.c:34:10: warning: assignment makes integer from pointer without a cast [-Wint-conversion]
s->fd=fopen("file.txt", "w+");
^
stack.c: In function 'push_stack':
stack.c:44:12: warning: passing argument 1 of 'fseek' makes pointer from integer without a cast [-Wint-conversion]
fseek (s->fd, 0, SEEK_END);
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:739:41: note: expected 'FILE * {aka struct _iobuf *}' but argument is of type 'int'
_CRTIMP __cdecl __MINGW_NOTHROW int fseek (FILE *, long, int);
^~~~~
stack.c:45:13: warning: passing argument 1 of 'fprintf' makes pointer from integer without a cast [-Wint-conversion]
fprintf(s->fd, "%d \n",val);
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:403:5: note: expected 'FILE * {aka struct _iobuf *}' but argument is of type 'int'
int fprintf (FILE *__stream, const char *__format, ...)
^~~~~~~
stack.c: In function 'pop_stack':
stack.c:52:11: warning: passing argument 1 of 'fseek' makes pointer from integer without a cast [-Wint-conversion]
fseek(s->fd,0,SEEK_CUR);
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:739:41: note: expected 'FILE * {aka struct _iobuf *}' but argument is of type 'int'
_CRTIMP __cdecl __MINGW_NOTHROW int fseek (FILE *, long, int);
^~~~~
stack.c:53:14: warning: passing argument 2 of 'fputs' makes pointer from integer without a cast [-Wint-conversion]
fputs("",s->fd);
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:675:41: note: expected 'FILE * {aka struct _iobuf *}' but argument is of type 'int'
_CRTIMP __cdecl __MINGW_NOTHROW int fputs (const char *, FILE *);
^~~~~
stack.c:54:16: warning: passing argument 1 of 'fgetc' makes pointer from integer without a cast [-Wint-conversion]
*val=fgetc(s->fd);
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:672:41: note: expected 'FILE * {aka struct _iobuf *}' but argument is of type 'int'
_CRTIMP __cdecl __MINGW_NOTHROW int fgetc (FILE *);
^~~~~
stack.c: In function 'display_stack':
stack.c:64:11: warning: passing argument 1 of 'fopen' makes pointer from integer without a cast [-Wint-conversion]
fopen(s->fd,"r+");
^
In file included from stack.c:19:0:
c:\mingw\include\stdio.h:260:41: note: expected 'const char *' but argument is of type 'int'
_CRTIMP __cdecl __MINGW_NOTHROW FILE * fopen (const char *, const char *);
^~~~~
stack.c: In function 'push_stack':
stack.c:48:1: warning: control reaches end of non-void function [-Wreturn-type]
} // push value into stack
^
stack.c: In function 'pop_stack':
stack.c:57:5: warning: control reaches end of non-void function [-Wreturn-type]
}
^
#ifndef STACK_FILE_H_INCLUDED
#define STACK_FILE_H_INCLUDED
#define MAX_FLNM 100
typedef struct {
char filename[MAX_FLNM];
int fd; // file descriptor of the open file
int top_off; // final offset
} stack_t;
void set_file(stack_t *); // special function to determine the file to be used
void init_stack(stack_t*); // initalize the data structure
int push_stack(stack_t *, int); // push value into stack
int pop_stack(stack_t *, int *); // pops top value from stack;
int top_stack(stack_t *, int *); // returns top value of stack
void display_stack(stack_t *); // displays the contents of the stack
#endif // STACK_FILE_H_INCLUDED
#include <stdio.h>
// #include "stack_file.h"
#include <string.h>
void set_file(stack_t *s)
{
FILE* file;
file=fopen("file.txt","w+");
printf("test set \n");
}
void init_stack(stack_t* s)
{
char nom []="file.txt";
strcpy(s->filename,nom);
s->fd=fopen("file.txt", "w+");
s->top_off=0;
printf("test init \n");
} // initalize the data structure
int push_stack(stack_t* s, int val)
{
printf("test push \n");
fseek (s->fd, 0, SEEK_END);
fprintf(s->fd, "%d \n",val);
} // push value into stack
int pop_stack(stack_t* s, int *val)
{
fseek(s->fd,0,SEEK_CUR);
fputs("",s->fd);
*val=fgetc(s->fd);
printf("test pop \n");
}
// pops top value from stack;
//int top_stack(stack_t *, int *); // returns top value of stack
void display_stack(stack_t* s)
{
printf("test display \n");
fopen(s->fd,"r+");
} // displays the contents of the stack
#include <stdio.h>
#include <stdlib.h>
//#include "stack_file.h"
int main() {
stack_t p;
set_file(&p);
init_stack(&p);
push_stack(&p, 5);
push_stack(&p, 6);
push_stack(&p, 7);
display_stack(&p);
scanf("%*c");
int val;
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val);
printf("popped value = %d\n", val);
display_stack(&p);
pop_stack(&p, &val); // fails
printf("popped value = %d\n", val); // prints out the old value
display_stack(&p);
}
- Edité par edgarjacobs 22 septembre 2018 à 17:39:46
On écrit "j'ai tort", pas "tord" qui est le verbe "tordre" à la 3ème personne de l'indicatif présent
Toutes les fonctions présentent un défaut, il va falloir les relire. D'autre part je n'arrive pas à relier ton code à l'énoncé. D'autant que que tu parles bien de stack ou de LIFO. Vue la structure de fichier que tu utilises (qui t'a peut-être été préconisée dans l'énoncé), le seul mécanisme implémentable est celui d'une FIFO (c-a-d une queue) donc le premier élément à extraire serait celui au début du fichier. Il manque des marqueurs ou le fichier devrait être à minima binaire. Difficile de t'aider sans mieux connaître l'énoncé et tes contraintes.
La première fonction set_file(): - elle reçoit un paramètre dont elle n'a rien à carrer! - elle ouvre un fichier et le crée vide s'il n'existe pas, mais perdle handle car il reste local à la fonction. Et donc se fichier restera bloqué ouvert jusqu'à la terminaison du programme (impossible de le refermer). Ce fichier sera réouvert en simultané ailleurs dans le code.
La seconde fonction init_stack(): - elle réouvre le fichier (elle connaît elle aussi son nom) mais stocke le handle dans un int. A ma connaissance c'est une erreur, les types sont incompatibles et ne sont même pas garantis de tailles identiques. Je suis étonné que gcc n'indique pas une erreur, et je n'imagine pas ce warning invisible.
La troisième fonction push_stack(): - c'est pas trop mal. - Mais pourquoi donc le s->top_off n'est pas mis à jour? Il faudrait comprendre à quoi il peut servir et donc relire l'énoncé.
...
En recherche d'emploi.
Lire et supprimer du contenu dans un fichier .txt
× Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
× Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
On écrit "j'ai tort", pas "tord" qui est le verbe "tordre" à la 3ème personne de l'indicatif présent
On écrit "j'ai tort", pas "tord" qui est le verbe "tordre" à la 3ème personne de l'indicatif présent
En recherche d'emploi.