Programación General > C/C++
[C] Estructuras y archivos binarios
Amphoth3ra:
Los problemas que yo tengo se relaciona con estructuras y con el guardado de estas estructuras y archivos binarios. Les explico el concepto: Lo que estoy buscando es almacenar una serie de parámetros a una estructura (rut, edad y nombre) y luego esta estructura se pasa a un archivo binario, el cual luego yo debo leerlo por atributo (sea rut, nombre o edad).
A mí me ocurren dos problemas con el programa que estoy haciendo. En primera instancia, el rut que yo introduzco inicialmente se introduce bien, pero cuando yo lo rescato del archivo binario la parte del rut me aparece con un caracter más del que yo puse originalmente, vale decir que si yo introduzco esta información:
Rut Edad Nombre
--------------------------------------------------------------------
12.346.812-7 52 Stephen Berger
Del archivo se me regresa lo siguiente:
Rut Edad Nombre
--------------------------------------------------------------------
12.346.812-74 52 Stephen Berger
Lo otro extraño que me pasa es que la última estructura que pongo se me duplica al rescatar la información del archivo binario, vale decir, si yo pongo esta información:
Rut Edad Nombre
--------------------------------------------------------------------
12.222.618-7 54 Jorge Contreras
12.228.164-4 59 Gerónimo Vallejos
13.433.618-K 47 Claudia Cotapos
Del archivo se me regresa esto:
Rut Edad Nombre
--------------------------------------------------------------------
12.222.618-76 54 Jorge Contreras
12.228.164-4; 59 Gerónimo Vallejos
13.433.618-K/ 47 Claudia Cotapos
13.433.618-K/ 47 Claudia Cotapos
Nótese que en lo anterior también se me repite el problema del rut, ustedes pueden ver que me sale un caracter adicional al rut.
Este es el código del programa:
--- Código: C ---#include <stdio.h>#include <stdlib.h>#include <string.h> struct persona { char rut[12]; int edad; char nombre[255]; }; // Declaración de tabla y creación del archivo con el que se vá a trabajar void create_table_personas() { FILE *principal_file, *test_file; principal_file = fopen ("archivo.dat", "wb"); if (principal_file==NULL) printf ("No se pudo crear el archivon"); fclose(principal_file); test_file = fopen ("archivo.dat", "rb"); if (test_file==NULL) printf ("No se pudo abrir el archivon"); rewind(test_file);} // Inserción en la tablavoid insert_into_table(){ int menu2_on = 1; struct persona avance; FILE *save_file; save_file = fopen ("archivo.dat", "r+wb"); fread (&avance, sizeof(struct persona), 1, save_file); if (avance.edad == 0) rewind(save_file); do { do { fread (&avance, sizeof(struct persona), 1, save_file); } while (!feof(save_file)); struct persona data_save; printf("Rut de la personan"); scanf("%*c%[^n]",data_save.rut); printf("Edad de la personan"); scanf("%d", &data_save.edad); printf("Nombre de la personan"); scanf("%*c%[^n]",data_save.nombre); fwrite (&data_save , 1 , sizeof(struct persona) , save_file); printf("¿Desea agregar otra tupla? (1 Si, 0 No)n"); scanf("%d", &menu2_on); } while (menu2_on == 1); fclose(save_file); struct persona junior; FILE *test_file; test_file = fopen ("archivo.dat", "rb"); if (test_file==NULL) printf ("No se pudo abrir el archivon"); printf("Rut Edad Nombren"); printf("--------------------------------------------------------------------n"); while (!feof(test_file)) { fread (&junior, sizeof(struct persona), 1, test_file); printf("%s %d %sn", junior.rut, junior.edad, junior.nombre); }} // Función: Consulta por edad //void attribute_age(){ FILE *checker; struct persona temporal; int edad_consulta; printf("Inserte la edad a consultarn"); scanf("%d",&edad_consulta); checker = fopen ("archivo.dat", "rb"); if (checker==NULL) printf ("No se pudo abrir el archivon"); rewind(checker); printf("Rut Edad Nombren"); printf("--------------------------------------------------------------------n"); do { fread (&temporal, sizeof(struct persona), 1, checker); if (edad_consulta == temporal.edad) { printf("%s %d %sn", temporal.rut, temporal.edad, temporal.nombre); } } while (!feof(checker)); } // Función: Consulta por nombrevoid attribute_name(){ FILE *checker2; struct persona temporal2; char nombre_consulta[255]; printf("Inserte el nombre a consultarn"); scanf("%*c%[^n]",nombre_consulta); checker2 = fopen ("archivo.dat", "rb"); if (checker2==NULL) printf ("No se pudo abrir el archivon"); rewind(checker2); printf("Rut Edad Nombren"); printf("--------------------------------------------------------------------n"); do { fread (&temporal2, sizeof(struct persona), 1, checker2); if (nombre_consulta == temporal2.nombre) { printf("%s %d %sn", temporal2.rut, temporal2.edad, temporal2.nombre); } } while (!feof(checker2)); } // Función: Consulta por rutvoid attribute_rut(){ FILE *checker3; struct persona temporal3; char rut_consulta[12]; printf("Inserte el rut a consultarn"); scanf("%*c%[^n]",rut_consulta); checker3 = fopen ("archivo.dat", "rb"); if (checker3==NULL) printf ("No se pudo abrir el archivon"); rewind(checker3); printf("Rut Edad Nombren"); printf("--------------------------------------------------------------------n"); do { fread (&temporal3, sizeof(struct persona), 1, checker3); if (rut_consulta == temporal3.rut) { printf("%s %d %sn", temporal3.rut, temporal3.edad, temporal3.nombre); } } while (!feof(checker3)); } // Función: Consulta completavoid generate_full(){ FILE *checker4; struct persona temporal4; checker4 = fopen ("archivo.dat", "rb"); if (checker4==NULL) printf ("No se pudo abrir el archivon"); rewind(checker4); printf("Rut Edad Nombren"); printf("--------------------------------------------------------------------n"); do { fread (&temporal4, sizeof(struct persona), 1, checker4); printf("%s %d %sn", temporal4.rut, temporal4.edad, temporal4.nombre); } while (!feof(checker4)); } // Menú secundario de búsqueda por atributo, void attribute_search(){ int menu3_option; do { printf("1 Consulta por rutn"); printf("2 Consulta por nombren"); printf("3 Consulta por edadn"); printf("4 Generar listado completon"); scanf("%d", &menu3_option); switch (menu3_option) { case 1: printf("n"); attribute_rut(); break; case 2: printf("n"); attribute_name(); break; case 3: printf("n"); attribute_age(); break; case 4: printf("n"); generate_full(); break; default: printf("Opcion invalidan"); break; } } while ((menu3_option < 1) || (menu3_option > 4));} // Opciones de menúint menu_option, menu_on = 1; // Menú principalint main (){ do { do { printf("n"); printf("1 Crear tablan"); printf("2 Insertar tuplasn"); printf("3 Ver contenidon"); scanf("%d", &menu_option); switch (menu_option) { case 1: printf("n"); create_table_personas(); break; case 2: printf("n"); insert_into_table(); break; case 3: printf("n"); attribute_search(); break; default: printf("n"); printf("Opcion invalidan"); break; } } while ((menu_option < 1) || (menu_option > 3)); printf("¿Desea realizar otra operacion? (1 Si, 0 No)n"); scanf ("%d", &menu_on); } while (menu_on == 1); return (0); }
Saludos.
alexg88:
El problema del 4 que aparece es porque no lees bien las cadenas.
Una cadena en C se representa como un conjunto de caracteres terminado con el caracter .
Tú al leer de la forma que lo haces ( scanf("%*c%[^n]",data_save.rut);) no le estás poniendo el al final y por eso al imprimir con %s te da problemas porque no sabe donde finaliza la cadena.
Para leer cadenas se utiliza %s también.
Sobre el segundo problema, da porque la función feof no te devuelve true cuando debería (estoy revisando porque).
Otra cosa, la línea 37 (en la función insert_into_table), abres mal el fichero (da un pedazo de error).
Incorrecto:
--- Código: C ---save_file = fopen ("archivo.dat", "r+wb");
Correcto (así abres para lectura y escritura):
--- Código: C ---save_file = fopen ("archivo.dat", "w+b");
Amphoth3ra:
--- Cita de: "alexg88" ---El problema del 4 que aparece es porque no lees bien las cadenas.
Una cadena en C se representa como un conjunto de caracteres terminado con el caracter .
Tú al leer de la forma que lo haces ( scanf("%*c%[^n]",data_save.rut);) no le estás poniendo el al final y por eso al imprimir con %s te da problemas porque no sabe donde finaliza la cadena.
Para leer cadenas se utiliza %s también.
--- Fin de la cita ---
¿Explícitamente que es lo que tengo que modificar? (si agrego me tira un aviso diciendo que el dice que está incrustado en el código).
Saludos.
alexg88:
Primero tienes que hacer el array rut un caracter más grande para que puedas poner el .
--- Código: C ---struct persona { char rut[12]; int edad; char nombre[255]; };
Segundo, las lecturas:
--- Código: C --- printf("Rut de la personan"); scanf("%s",data_save.rut); printf("Edad de la personan"); scanf("%d", &data_save.edad); printf("Nombre de la personan"); scanf("%s",data_save.nombre);
Ya se porque te falla el feof. Resulta que para que feof te diga si el fichero ha terminado primero tienes que leer y luego realizar feof. Por eso te entra dos veces.
Tendrías que hacerlo así:
--- Código: C --- void insert_into_table(){ void insert_into_table(){ int menu2_on = 1; struct persona avance; FILE *save_file; save_file = fopen ("archivo.dat", "w+b"); fread (&avance, sizeof(struct persona), 1, save_file); if (avance.edad == 0) rewind(save_file); do { fread (&avance, sizeof(struct persona), 1, save_file); do { fread (&avance, sizeof(struct persona), 1, save_file); } while (!feof(save_file)); struct persona data_save; printf("Rut de la personan"); scanf("%s",data_save.rut); printf("Edad de la personan"); scanf("%d", &data_save.edad); printf("Nombre de la personan"); scanf("%s",data_save.nombre); fwrite (&data_save , 1 , sizeof(struct persona) , save_file); printf("¿Desea agregar otra tupla? (1 Si, 0 No)n"); scanf("%d", &menu2_on); } while (menu2_on == 1); fclose(save_file); struct persona junior; FILE *test_file; test_file = fopen ("archivo.dat", "rb"); if (test_file==NULL) printf ("No se pudo abrir el archivon"); printf("RuttEdadtNombren"); printf("--------------------------------------------------------------------n"); fread (&junior, sizeof(struct persona), 1, save_file); while (!feof(test_file)) { printf("%st%dt%sn", junior.rut, junior.edad, junior.nombre); fread (&junior, sizeof(struct persona), 1, test_file); }}
Amphoth3ra:
De ahí te cuento como me salió, no te puedo decir mucho, pero solucioné los dos problemas que tenía.
Saludos.
Navegación
[#] Página Siguiente
Ir a la versión completa