Loading a structure (text lines) from a file, modify the structure, then save

Please support our C advertiser: Programming Forums - DaniWeb Sister Site
Reply

Join Date: May 2008
Posts: 82
Reputation: riahc3 is an unknown quantity at this point 
Solved Threads: 0
riahc3 riahc3 is offline Offline
Junior Poster in Training

Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #1
May 13th, 2008
Hey everyone. Glad to become part of this community and I hope I continue to come here for a long time seeing as this site gives great helps. My problem:

I have a struct that is (for example) the following:

  1.  
  2. #define NUM 999
  3.  
  4. struct client
  5. {
  6. int id;
  7. char name[15];
  8. char lastname[15];
  9. int telephone;
  10. }c[NUM];

I want to do the following: First I want to see if the file exists or not. Thats pretty simple using a pointer to the fopen function with the file; If it returns NULL it doesnt exist. Now the hard part is reading and loading and then after saving.

If it isnt found, all the struct will be set to the number/string 0. If its found, then all of the data from the text file is loaded onto the struct and I work with the struct modifing, deleteing, adding, etc.
At the end of the program when I hit enter, Id like for the program to save all (or the changes) to the text file so when I load the program again it has all the additions I previously made.

If Im not clear on something, go ahead and ask. Thank you very much for your help.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 351
Reputation: Radical Edward has a spectacular aura about Radical Edward has a spectacular aura about Radical Edward has a spectacular aura about 
Solved Threads: 62
Radical Edward's Avatar
Radical Edward Radical Edward is offline Offline
Posting Whiz

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #2
May 13th, 2008
> If Im not clear on something, go ahead and ask.
What is it you want? Edward prefers to see the best in others, but if you only post the requirements of your program, at least one person is going to think you want it all written for you.

It's best to post your current attempt and ask for specific help about the code or the design. Then it's easy to see that you're just having a little trouble and not looking for a free ride. You'll also get better help because people like Ed can focus on the trouble areas and ignore the areas that you've got covered.
If at first you don't succeed, keep on sucking until you do succeed.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 376
Reputation: Clockowl is on a distinguished road 
Solved Threads: 27
Clockowl's Avatar
Clockowl Clockowl is offline Offline
Posting Whiz

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #3
May 13th, 2008
So first you open it, then you read it in, parse the file in your structure, and move on to the next.

Reading in a file: fread()
Parsing: Your own mix and a bit of sscanf();

writing would be exactly the opposite: sprintf() and fwrite().

sprintf and sscanf work like printf and scanf, except the first argument is a pointer to a character array which is read from/printed to.
Last edited by Clockowl; May 13th, 2008 at 11:58 am. Reason: Typo's
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 82
Reputation: riahc3 is an unknown quantity at this point 
Solved Threads: 0
riahc3 riahc3 is offline Offline
Junior Poster in Training

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #4
May 13th, 2008
Id like to post the code but its in spanish so it wouldnt help much.

I tried just making a typedef with a *cl but the problem is I cant go thru each 999 of the clients (c[num]). What Id like to do is point the *cl pointer to c[num] and somehow run thru it such as *cl[num] (I know a array is already a pointer so it wont work.)

If there is any part that I could describe so someone can help me, just say.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 376
Reputation: Clockowl is on a distinguished road 
Solved Threads: 27
Clockowl's Avatar
Clockowl Clockowl is offline Offline
Posting Whiz

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #5
May 13th, 2008
You really oughta post some of the code here. I'm sure most people here have dealt with oddly name variables.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 82
Reputation: riahc3 is an unknown quantity at this point 
Solved Threads: 0
riahc3 riahc3 is offline Offline
Junior Poster in Training

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #6
May 13th, 2008
OK here's the code for my structs:

  1. #define num 999 // Para que sean todos las estructuras de 999
  2.  
  3. /* Estructuras principales */
  4. struct direccion
  5. {
  6. char calle[15]; //Limitado a 15 characteres
  7. int numportal; //1 digito
  8. int piso; //1 digito
  9. };
  10. struct poblacion
  11. {
  12. char nombrepoblacion[15]; //Limitado a 15 characteres
  13. int codpostal; //Limitado a 5 digitos
  14. char provincia[15]; //Limitado a 15 characteres
  15. };
  16.  
  17. struct empleados
  18. {
  19. int id; // Limitado a una letra E seguido de 3 numeros
  20. char dni[11]; //Limitado a 8 numeros, un guion y una letra
  21. char nombre[15]; //Limitado a 15 characteres
  22. char apellido[15]; //Limitado a 15 characteres
  23. int telefono; //Limitado a 9 digitos
  24. struct direccion dir; // Una variable que es de tipo estructura dirrecion: acesso a calle,
  25. //Numportal, y piso
  26. struct poblacion pob; // Una variable que es de tipo estructura poblacion: accesso a
  27. // nombrepoblacion, codpostal, y provincia
  28. }e[num];
  29. /* Asi podemos insertar hasta 999 productos, porque he creado
  30. la tabla que contiene num elementos de tipo empleados: Este numero es el mismo que el id */
  31.  
  32.  
  33.  
  34. struct clientes
  35. {
  36. int id; // Limitado a una letra C seguido de 3 numeros
  37. char dni[11]; //Limitado a 8 numeros, un espacio y una letra
  38. char nombre[15];//Limitado a 15 characteres
  39. char apellido[15];//Limitado a 15 characteres
  40. int telefono;//Limitado a 6 digitos
  41. struct direccion dir; // Una variable que es de tipo estructura dirrecion: acesso a calle,
  42. //Numportal, y piso
  43. struct poblacion pob; // Una variable que es de tipo estructura poblacion: accesso a
  44. // nombrepoblacion, codpostal, y provincia
  45. int cantcompras; // La cantidad de comprars para los descuentos
  46.  
  47. }c[num];
  48. /* Asi podemos insertar hasta 999 productos, porque he creado
  49. la tabla que contiene num elementos de tipo cliente: Este numero es el mismo que el id */
  50.  
  51.  
  52.  
  53.  
  54. struct productos
  55. {
  56.  
  57. int id; // Limitado a una letra P seguido de 3 numeros
  58. char nombre[15]; //Limitado a 15 characteres
  59. char descripcion[50]; //Limitado a 50 characteres
  60. float precio; // Precio con decimal
  61. int cantidad; //Lo que queda en stock
  62.  
  63. }p[num];
  64. /* Asi podemos insertar hasta 999 productos, porque he creado
  65. la tabla que contiene num elementos de tipo producto: Este numero es el mismo que el id */

Ill explain:

p is a variable that I can use to access each field. It is a array so I can access all 999 possible clients in the struct (why? explanation below

  1. void inicializar ()
  2. { // Principio de funciones inicizalizar
  3. int a=0; // 1 Contador
  4.  
  5. /********************* Inicializamos la estructura de clientes *************************/
  6. /* Campos int id, char dni, char nombre, char apellido, int telefono */
  7.  
  8.  
  9. for (a=0;a<999;a++)
  10. {
  11.  
  12. c[a].id=0;
  13. strcpy(c[a].dni,"0");
  14. strcpy(c[a].nombre,"0");
  15. strcpy(c[a].apellido,"0");
  16. c[a].telefono=0;
  17. c[a].cantcompras=0;
  18. strcpy(c[a].dir.calle,"0");
  19. c[a].dir.numportal=0;
  20. c[a].dir.piso=0;
  21. c[a].pob.codpostal=0;
  22. strcpy(c[a].pob.nombrepoblacion,"0");
  23. strcpy(c[a].pob.provincia,"0");
  24. }
  25. /***************** Fin de inicializacion de clientes ******************************/
  26.  
  27.  
  28. /********************* Inicializamos la estructura de empleados *************************/
  29. /* Campos: int id, char dni, char nombre, char apellido, int telefono */
  30.  
  31. for (a=0;a<999;a++)
  32. {
  33.  
  34. e[a].id=0;
  35. strcpy(e[a].dni,"0");
  36. strcpy(e[a].nombre,"0");
  37. strcpy(e[a].apellido,"0");
  38. e[a].telefono=0;
  39. strcpy(e[a].dir.calle,"0");
  40. e[a].dir.numportal=0;
  41. e[a].dir.piso=0;
  42. e[a].pob.codpostal=0;
  43. strcpy(e[a].pob.nombrepoblacion,"0");
  44. strcpy(e[a].pob.provincia,"0");
  45.  
  46.  
  47. }
  48. /********************* Fin de inicializacion de empleados ******************************/
  49.  
  50.  
  51.  
  52.  
  53.  
  54. /***************** Inicializamos la estructura de productos ***********************/
  55.  
  56. for (a=0;a<999;a++) // Este for permite que cada 999 de los productos lo ponga a 0
  57. {
  58. p[a].id=0;
  59. strcpy(p[a].nombre,"0");
  60. strcpy(p[a].descripcion,"0");
  61. p[a].precio=0.0;
  62. p[a].cantidad=0;
  63. }
  64.  
  65. /***************** Fin de inicializacion de productos ******************************/
  66.  
  67. } // Fin de funciones de inicializar

As you can see I set here all values to 0. Why? Because I use 0 or "0" as a wildcard for some function to see if the client's empty or not.

The point is that I have to do all of this (add,modify,delete,etc) using a pointer that acceses a file instead of setting it values. In this file, I should have all of the fields and everytime I load the program it sets the values in the file to the struct. I work locally with the struct and when I end the program it saves all of it to a file. I have this so far:

  1. void inicializarporarchivo()
  2. {
  3. FILE *ficheroc;
  4. FILE *ficheroe;
  5. FILE *ficherop;
  6. int i;
  7. char tid[1];
  8. char ttelefono[9];
  9. char tcantcompras[1];
  10. char tnumportal[2];
  11. char tpiso[1];
  12.  
  13. ficheroc=fopen("clientes.txt","r");
  14. ficheroe=fopen("empleados.txt","r");
  15. ficherop=fopen("productos.txt","r");
  16. if (ficheroc==NULL)
  17. {
  18. void inicializar();
  19. }
  20.  
  21. /* fclose(ficheroc);
  22. ficheroc=fopen("clientes.txt","w");
  23. for (i=0;i<999;i++)
  24. {
  25. fputs("Cliente ",ficheroc);
  26. fputc(i,ficheroc);
  27. fputs(":",ficheroc);
  28. fputc("0",ficheroc);
  29. fputc("0",ficheroc);
  30. fputc("0",ficheroc);
  31. fputc("0",ficheroc);
  32. fputc("0",ficheroc);
  33. fputc("0",ficheroc);
  34. fputc("0",ficheroc);
  35. fputc("0",ficheroc);
  36. fputc("0",ficheroc);
  37. fputc("0",ficheroc);
  38. fputc("0",ficheroc);
  39. fputc("0",ficheroc);
  40. fputs("\n",ficheroc);
  41. }*/
  42.  
  43. if (ficheroc!=NULL)
  44. {
  45. do
  46. {
  47. for (i=0;i<999;i++)
  48. {
  49. fgets(tid,sizeof(tid),ficheroc);
  50. c[i].id=atoi(tid);
  51. fgets(c[i].dni,sizeof(c[i].dni),ficheroc);
  52. fgets(c[i].nombre,sizeof(c[i].nombre),ficheroc);
  53. fgets(c[i].apellido,sizeof(c[i].apellido),ficheroc);
  54. fgets(ttelefono,sizeof(ttelefono),ficheroc);
  55. c[i].telefono=atoi(ttelefono);
  56. fgets(tcantcompras,sizeof(tcantcompras),ficheroc);
  57. c[i].cantcompras=atoi(tcantcompras);
  58. fgets(c[i].dir.calle,sizeof(c[i].dir.calle),ficheroc);
  59. fgets(tnumportal,sizeof(tnumportal),ficheroc);
  60. c[i].dir.numportal=atoi(tnumportal);
  61. fgets(tpiso,sizeof(tpiso),ficheroc);
  62. c[i].dir.piso=atoi(tpiso);
  63. fgets(c[i].dir.calle,sizeof(c[i].dir.calle),ficheroc);
  64. fgets(c[i].pob.nombrepoblacion,sizeof(c[i].pob.nombrepoblacion),ficheroc);
  65. fgets(c[i].pob.provincia,sizeof(c[i].pob.provincia),ficheroc);
  66. printf ("%s",c[i].dni);
  67. getch();
  68. }
  69. putc("\0",ficheroc);
  70. }while (feof(ficheroc)!=1);
  71. }
  72.  
  73. }

But it doesnt work nor does it use a pointer.
Objectives:

1: Use a pointer to access the data in each field.
2: Load/save from/to a file.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 376
Reputation: Clockowl is on a distinguished road 
Solved Threads: 27
Clockowl's Avatar
Clockowl Clockowl is offline Offline
Posting Whiz

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #7
May 14th, 2008
in inicializar():
I wouldn't initialize strings like that. Better to use memset to clear them, or only set the first byte to the NULL byte. Doesn't really matter, but it makes the code a bit more readable. I think.

in inicializarporarchivo:
char tid[1];
char ttelefono[9];
char tcantcompras[1];
char tnumportal[2];
char tpiso[1];

tid, tcantcompras, tpiso: char arrays of a single char?

How do your files look? Your only using fgets, which reads in a file until it encounters a '\n'. Is that correct?

You're trying to use putc on a file which you opened as "r"eadonly. That' can't be correct.

You're testing "feof()" with "!= 1". Better would it be to continue when "feof == 0", since TRUE isn't defined as 1 but as any non-zero number.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 82
Reputation: riahc3 is an unknown quantity at this point 
Solved Threads: 0
riahc3 riahc3 is offline Offline
Junior Poster in Training

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #8
May 14th, 2008
Originally Posted by Clockowl View Post
in inicializar():Better to use memset to clear them, or only set the first byte to the NULL byte.
I havent read anythning about that so that isnt a option

Originally Posted by Clockowl View Post
in inicializarporarchivo:
char tid[1];
char ttelefono[9];
char tcantcompras[1];
char tnumportal[2];
char tpiso[1];

tid, tcantcompras, tpiso: char arrays of a single char?
Yes that was kind of stupid because I was stressed.

Originally Posted by Clockowl View Post
How do your files look? Your only using fgets, which reads in a file until it encounters a '\n'. Is that correct?
I dont understand this very well but my files are like this:

Client 1:
1234567-L
David
James

So each line (\n) is read and inserted into each field in the struct. Is that the correct way to do it?


Originally Posted by Clockowl View Post
You're trying to use putc on a file which you opened as "r"eadonly. That' can't be correct.
I dont use putc in anywhere...except maybe when it is NULL and it has to close and open it as write...

Originally Posted by Clockowl View Post
You're testing "feof()" with "!= 1". Better would it be to continue when "feof == 0", since TRUE isn't defined as 1 but as any non-zero number.
Reexplain this please.
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 376
Reputation: Clockowl is on a distinguished road 
Solved Threads: 27
Clockowl's Avatar
Clockowl Clockowl is offline Offline
Posting Whiz

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #9
May 14th, 2008
If you need to reopen it for writing, why don't you open it for reading and writing "rw" or reopen it with freopen()?

feof() returns a nonzero value when the FILE* has reached the EOF. Your while-loop checks if it doesn't equal one, but it should check if it equals 0: it may not return 1, it may return any nonzero number. This doesn't have to be a problem, but it's more secure.

If you haven't read anything about memset, you don't know how to initialize arrays. Which is kinda bad. You can set the whole c[], p[] and other arrays to 0 or any value you prefer with memset. Read up on it. It'd make the program more readable and faster.

By the way, here's a nice reference:
c(pp)reference
Last edited by Clockowl; May 14th, 2008 at 7:26 pm. Reason: Added reference URL
Reply With Quote Quick reply to this message  
Join Date: May 2008
Posts: 82
Reputation: riahc3 is an unknown quantity at this point 
Solved Threads: 0
riahc3 riahc3 is offline Offline
Junior Poster in Training

Re: Loading a structure (text lines) from a file, modify the structure, then save

 
0
  #10
May 14th, 2008
Originally Posted by Clockowl View Post
If you need to reopen it for writing, why don't you open it for reading and writing "rw" or reopen it with freopen()?
Because Ive been show that its more secure to open and close it....
Don't know about freopen.


Originally Posted by Clockowl View Post
feof() returns a nonzero value when the FILE* has reached the EOF. Your while-loop checks if it doesn't equal one, but it should check if it equals 0: it may not return 1, it may return any nonzero number. This doesn't have to be a problem, but it's more secure.
I understand and Ill fix this

Originally Posted by Clockowl View Post
If you haven't read anything about memset, you don't know how to initialize arrays. Which is kinda bad. You can set the whole c[], p[] and other arrays to 0 or any value you prefer with memset. Read up on it. It'd make the program more readable and faster.
Well to initialize a array we weren't shown using memset....

Originally Posted by Clockowl View Post
By the way, here's a nice reference:
c(pp)reference
[/quote]
Thanks.

Thanks BTW for all your help Clockowl.

I have another question but related.

As you see I have

c[num] for my structs.
How can I use a pointer to go thru all 999 positions for the struct? Pointers and file handling are my weakpoints; Any more pages about these subjects would be great. Again thanks Clockowl
Reply With Quote Quick reply to this message  
Reply

This thread is more than three months old.
Perhaps start a new thread instead?
Message:



Other Threads in the C Forum
Thread Tools Search this Thread



Tag cloud for C
About Us | Contact Us | Advertise | DaniWeb | Acceptable Use Policy | RSS Feed

©2003 - 2009 DaniWeb® LLC