Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: ++c en 25 Agosto 2014, 22:49 pm



Título: Ayuda con este código de archivos
Publicado por: ++c en 25 Agosto 2014, 22:49 pm
Hola amigos,
tengo un problema con este código basado en archivos y no entiendo porque
en esta parte del programa me lee toda la cadena, cuando esperaba solo leyera y me mostrara por pantalla el nombre de la persona y no toda la cadena seguida de nombre, ciudad y edad.

Código
  1.  
  2.        fgets(persona.nombre,40,fichero);
  3.        puts(persona.nombre);
  4.  
  5.  

Este es el código completo:

Código
  1.  
  2. #include <stdio.h>
  3. #include <string.h>
  4.  
  5. struct informe{
  6.    char nombre[40];
  7.    char ciudad[40];
  8.    int edad;
  9. }persona;
  10.  
  11. int main()
  12. {
  13.    char name[20]="gente.dat";
  14.    FILE *fichero;
  15.    fichero=fopen(name,"w");
  16.    if(fichero==NULL){
  17.        printf("\nEl archivo no existe\n");
  18.        exit(1);
  19.    }
  20.    else{
  21.        /*Escribo el archivo*/
  22.        printf("Introduzca nombre: ");
  23.        gets(persona.nombre);
  24.        fprintf(fichero,"%s",persona.nombre);
  25.        printf("Introduzca ciudad: ");
  26.        gets(persona.ciudad);
  27.        fprintf(fichero,"%s",persona.ciudad);
  28.        printf("Introduzca edad: ");
  29.        scanf("%d",&persona.edad);
  30.        fprintf(fichero,"%d",persona.edad);
  31.        fclose(fichero);
  32.    }
  33.  
  34.    /* Leo el archivo */
  35.    printf("\nEsto es lo que se ha introducido en el archivo:\n\n");
  36.    printf("_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _\n\n");
  37.    fichero=fopen(name,"r");
  38.    if(fichero==NULL){
  39.        printf("\nEl archivo no existe\n");
  40.        exit(1);
  41.    }
  42.    while(feof(fichero)==0){
  43.  
  44.        fgets(persona.nombre,40,fichero);
  45.        puts(persona.nombre);
  46.        fgets(persona.ciudad,40,fichero);
  47.        puts(persona.ciudad);
  48.        fscanf(fichero,"%d",&persona.edad);
  49.        puts(persona.edad);
  50.    }
  51.    fclose(fichero);
  52. return 0;
  53. }
  54.  

Gracias, un saludo


Título: Re: Ayuda con este código de archivos
Publicado por: rir3760 en 26 Agosto 2014, 04:09 am
El problema se genera por la forma en que guardas los datos en el archivo:
Código
  1. /*Escribo el archivo*/
  2. printf("Introduzca nombre: ");
  3. gets(persona.nombre);
  4. fprintf(fichero,"%s",persona.nombre);
  5.  
  6. printf("Introduzca ciudad: ");
  7. gets(persona.ciudad);
  8. fprintf(fichero,"%s",persona.ciudad);
  9.  
  10. printf("Introduzca edad: ");
  11. scanf("%d",&persona.edad);
  12. fprintf(fichero,"%d",persona.edad);
  13.  
  14. fclose(fichero);
Por ejemplo si el nombre es "X", la ciudad "Y" y la edad "5" los datos se envían sin separación alguna como la secuencia "XY5".

Para solucionarlo debes enviar cada campo seguido de un avance de linea:
Código
  1. /*Escribo el archivo*/
  2. printf("Introduzca nombre: ");
  3. gets(persona.nombre);
  4. fprintf(fichero, "%s\n", persona.nombre);
  5.  
  6. printf("Introduzca ciudad: ");
  7. gets(persona.ciudad);
  8. fprintf(fichero, "%s\n", persona.ciudad);
  9.  
  10. printf("Introduzca edad: ");
  11. scanf("%d", &persona.edad);
  12. fprintf(fichero, "%d\n", persona.edad);
  13.  
  14. fclose (fichero);

Otros errores que debes corregir:

* Antes de utilizar la función exit debes incluir el encabezado <stdlib.h>.

* No puedes imprimir un entero (la edad) con la función puts:
Código
  1. fscanf(fichero,"%d",&persona.edad);
  2. puts(persona.edad);
En lugar de puts utiliza printf.

* Después de leer el ultimo campo de tipo int (de nuevo la edad) debes descartar el resto de la linea.

* La condición del bucle de lectura garantiza un iteración de mas, en otras palabras si tienes un registro se trataran de mostrar dos. Para evitarlo debes verificar (por lo menos) el resultado de la lectura del primer campo. Combinado con el punto anterior:
Código
  1. while (fgets(persona.nombre, 40, fichero) != NULL){
  2.   printf("%s", persona.nombre);
  3.  
  4.   fgets(persona.ciudad, 40, fichero);
  5.   printf("%s", persona.ciudad);
  6.  
  7.   fscanf(fichero,"%d",&persona.edad);
  8.   printf("%d\n", persona.edad);
  9.  
  10.   {
  11.      int ch;
  12.  
  13.      while ((ch = fgetc(fichero)) != EOF && ch != '\n')
  14.         ;
  15.   }
  16. }
  17. fclose(fichero);

Por ultimo debes evitar el uso de magic numbers y las funciones gets y feof. Mas información en la pagina |Lo que no hay que hacer en C/C++. Nivel basico| (http://foro.elhacker.net/programacion_cc/lo_que_no_hay_que_hacer_en_cc_nivel_basico-t277729.0.html).

Un saludo


Título: Re: Ayuda con este código de archivos
Publicado por: ++c en 26 Agosto 2014, 21:20 pm
Hola rir3760,

pufff que nivel, como te agradezco tu inmejorable explicación. La verdad que más claro y educativo imposible.

Saludos master!!

Pdata: buen post el que me indicaste, muchas veces tenemos las cosas enfrente de nuestros ojos y nos las vemos o el subsconciente nos juega malas pasadas, jajaja