Hoy tuve examen de C, está vez tocaba ficheros y estructuras. Como viene siendo tradicional por mi parte, tenéis a vuestra disposición el ejercicio tal cual lo presente en el examen. El ejercicio nos pedía utilizar una estructura, propuesta en el ejercicio, para almacenar en un fichero los datos sobre los productos de un almacén, para ello contamos con el fichero almacen.dat donde tenemos los productos después de ser actualizados y un fichero cambios.dat donde tendremos los datos que han sido borrados, modificados o creados partiendo de los datos guardados en almacen.dat. Para guardar estos cambios en el fichero almacen.dat debemos llamar a una función actualizar( ); y almacenar o borrar si procede los datos que están en cambios.dat a el fichero almacen.dat, para lo que podemos utilizar un tercer fichero auxiliar.

No me lío más y aquí tenéis el fuente del programa. Para aclarar dudas preguntar por Makumba, el muchacho tiene respuestas para todo jeje.

Descargar | Código Fuente

C:
  1. #include <stdio .h>
  2. #include <conio .h>
  3. #include <stdlib .h>
  4. #include <string .h>
  5. typedef struct almacen
  6. {
  7.     char codigo[5];
  8.     char descripcion[61];
  9.     int precio;
  10.     int cantidad;
  11. }producto;
  12.  
  13. void cargar();
  14. void visualizar(char nombre[40]);
  15. int menu();
  16. void borrar();
  17. void actualizar();
  18. void modificar();
  19. void ordenar();
  20.  
  21. void main()
  22. {
  23.     int opcion;
  24.         do{
  25.             opcion=menu();
  26.             switch(opcion)
  27.             {
  28.                 case 1:
  29.                     clrscr();
  30.                     visualizar("almacen.dat");
  31.                     printf("\n\nPresione una tecla para continuar");
  32.                     getche();
  33.                     break;
  34.                 case 2:
  35.                     clrscr();
  36.                     cargar();
  37.                     break;
  38.                 case 3:
  39.                     clrscr();
  40.                     printf("\n\t\t::SE HA BORRADO CORRECTAMENTE EL REGISTRO::");
  41.                     borrar();
  42.                     break;
  43.                 case 4:
  44.                     clrscr();
  45.                     printf("\n\t\t::SE HA MODIFICADO SATISFACTORIAMENTE EL REGISTRO::");
  46.                     modificar();
  47.                     break;
  48.                 case 5:
  49.                     clrscr();
  50.                     actualizar();
  51.                     printf("\n\t\t::SE HA ACTUALIZADO EL FICHERO CON EXITO::");
  52.                     printf("\n\nPresione una tecla para continuar");
  53.                     getche();
  54.                     break;
  55.                 case 6:
  56.                     clrscr();
  57.                     visualizar("cambios.dat");
  58.                     printf("\n\nPresione una tecla para continuar");
  59.                     getche();
  60.                     break;
  61.                 case 7:
  62.                     clrscr();
  63.                     ordenar();
  64.                     printf("\n\t\t::SE HA ORDENADO EL FICHERO::");
  65.                     printf("\n\nPresione una tecla para continuar");
  66.                     getche();
  67.                     break;
  68.                 case 8:
  69.                     clrscr();
  70.                     opcion=9;
  71.                     break;
  72.                 default:
  73.                     menu();
  74.             }
  75.         }while(opcion!=9);
  76. }
  77.  
  78. int menu()
  79. {
  80.     int resp;
  81.     do{
  82.         clrscr();
  83.         printf("----------------------------------------------------------------------\n");
  84.         printf("[1].- Visualizar el fichero almacen.dat.\n");
  85.         printf("[2].- Añadir un nuevo producto.\n");
  86.         printf("[3].- Borrar un producto.\n");
  87.         printf("[4].- Modificar datos de un producto.\n");
  88.         printf("[5].- Actualizar el fichero alumnos con los cambios.\n");
  89.         printf("[6].- Visualizar el fichero cambios.dat.\n");
  90.       printf("[7].- Ordenar fichero almacen.dat.\n");
  91.         printf("[8].- Salir.\n");
  92.         printf("----------------------------------------------------------------------\n\n");
  93.         printf("\t\t\tIntroducir opcion: ");
  94.         scanf("%d",&resp); fflush(stdin);
  95.     }while(resp!=1 && resp!=2 && resp!=3 && resp!=4 && resp!=5 && resp!=6 && resp!=7 && resp!=8);
  96.     return(resp);
  97. }
  98.  
  99. void visualizar(char nombre[40])
  100. {
  101.     //pasamos como argumento el nombre del fichero para que sirva
  102.     //para ambos ficheros.
  103.  
  104.     //usamos funcion gotoxy para situar los datos en pantalla
  105.     FILE *fichero;
  106.     producto pro;
  107.     int i;
  108.     if((fichero=fopen(nombre, "rb"))==NULL)
  109.     {
  110.         printf("No se puede abrir el fichero.\n");
  111.         exit(1);
  112.     }
  113.     gotoxy(1,1);
  114.     printf("CODIGO");
  115.     gotoxy(15,1);
  116.     printf("DESCRIPCION");
  117.     gotoxy(50,1);
  118.     printf("PRECIO");
  119.     gotoxy(60,1);
  120.     printf("CANTIDAD");
  121.     for(i=1; i&lt;70; i++)
  122.     {
  123.         gotoxy(i,2);
  124.         printf("=");
  125.     }
  126.     i=3;
  127.     while(fread(&pro, sizeof(producto), 1, fichero)!=NULL)
  128.     {
  129.         gotoxy(1,i);
  130.         printf("%s ", pro.codigo);
  131.         gotoxy(15,i);
  132.         printf("%s ", pro.descripcion);
  133.         gotoxy(50,i);
  134.         printf("%d ", pro.precio);
  135.         gotoxy(60,i);
  136.         printf("%d ", pro.cantidad);
  137.         i++;
  138.     }
  139.     fclose(fichero);
  140. }
  141.  
  142. void cargar()
  143. {
  144.     //nuevos datos que seran almacenados en el fichero  cambios.dat
  145.     FILE *fichero;
  146.     producto pro;
  147.     char resp;
  148.  
  149.     if((fichero=fopen("cambios.dat", "a+b"))==NULL)
  150.     {
  151.         printf("No se puede abrir el fichero.\n");
  152.         exit(1);
  153.     }
  154.     do{
  155.         printf("\n:::Añadir un nuevo producto:::\n\n");
  156.         printf("Codigo: ");
  157.         gets(pro.codigo);
  158.         fflush(stdin);
  159.         printf("\nDescripcion: ");
  160.         gets(pro.descripcion);
  161.         fflush(stdin);
  162.         printf("\nPrecio: ");
  163.         scanf("%d", &pro.precio);
  164.         fflush(stdin);
  165.         printf("\nCantidad: ");
  166.         scanf("%d", &pro.cantidad);
  167.         fflush(stdin);
  168.         printf("\n¿Desea introducir otro producto [s/n]? ");
  169.         scanf("%c", &resp);fflush(stdin);
  170.         fwrite(&pro, sizeof(producto), 1, fichero);
  171.     }while(resp!='n');
  172.     fclose(fichero);
  173. }
  174. void borrar()
  175. {
  176.     //los ficheros para borrar en la proxima actualizacion, marcados con
  177.     //pro.codigo=-1 para identificarlos en la actualizacion
  178.     FILE *modificado, *original;
  179.     char mod[40];
  180.     producto pro;
  181.     visualizar("almacen.dat");
  182.     if((modificado=fopen("cambios.dat", "a+b"))==NULL || (original=fopen("almacen.dat", "r+b"))==NULL)
  183.     {
  184.         printf("No se pueden abrir los ficheros.\n");
  185.         exit(1);
  186.     }
  187.     printf("\n\n\Indique el CODIGO del producto que desea borrar: ");
  188.     gets(mod); fflush(stdin);
  189.     while(fread(&pro, sizeof(producto), 1, original)!=NULL)
  190.     {
  191.       if(strcmp(mod,pro.codigo)==0)
  192.       {
  193.         pro.cantidad=-1;
  194.         fwrite(&pro,sizeof(producto),1,modificado);
  195.       }
  196.     }
  197.     fclose(modificado);
  198.     fclose(original);
  199. }
  200.  
  201. void actualizar()
  202. {
  203.     FILE *fichero, *modificado, *temporal;
  204.     //en el fichero temporal incluimos los registros antiguos, actualizados.
  205.     producto pro;
  206.     producto pro_mod;
  207.     int sw=0;
  208.     long int tam=sizeof(pro);
  209.     if((fichero=fopen("almacen.dat", "r+b"))==NULL
  210.     || (modificado=fopen("cambios.dat", "r+b"))==NULL
  211.     || (temporal=fopen("temporal.dat", "a+b"))==NULL)
  212.     {
  213.         printf("No se pueden abrir los ficheros.\n");
  214.         exit(1);
  215.     }
  216.     while(fread(&pro_mod, sizeof(producto), 1, modificado)!=NULL)
  217.     {
  218.         fseek(fichero,0L,SEEK_SET);
  219.         while(fread(&pro, sizeof(producto), 1, fichero)!=NULL)
  220.         {
  221.             if(strcmp(pro_mod.codigo,pro.codigo)==0)
  222.             {
  223.                 //guardamos los registros que han cambiado
  224.                 //no copiamos los productos que se van a eliminar
  225.                 if (pro_mod.cantidad!=-1)
  226.                     fwrite(&pro_mod, sizeof(producto), 1, temporal);
  227.                 sw=1;
  228.  
  229.             }
  230.         }
  231.         if (sw==0)
  232.         {
  233.             //guardamos los nuevos registros
  234.             fwrite(&pro_mod, sizeof(producto), 1, temporal);
  235.             sw=0;
  236.         }
  237.     }
  238.  
  239.     //Para los registros antiguos
  240.     sw=0;
  241.     fseek(fichero,0L,SEEK_SET);
  242.     while(fread(&pro, sizeof(producto), 1, fichero)!=NULL)
  243.     {
  244.         fseek(modificado,0L,SEEK_SET);
  245.         while(fread(&pro_mod, sizeof(producto), 1, modificado)!=NULL)
  246.         {
  247.             //recorremos los modificado para ver si el producto original no ha sido
  248.             //tocado
  249.             if(strcmp(pro_mod.codigo,pro.codigo)==0)
  250.                 sw=1;
  251.         }
  252.         if (sw==0)
  253.         {
  254.             //guardamos los antiguos registros
  255.             fwrite(&pro, sizeof(producto), 1, temporal);
  256.         }
  257.         sw=0;
  258.     }
  259.     fclose (fichero);
  260.     remove ("almacen.dat");
  261.     fclose (modificado);
  262.     remove ("cambios.dat");
  263.     fclose (temporal);
  264.     rename ("temporal.dat","almacen.dat");
  265. }
  266. void modificar()
  267. {
  268.     FILE *modificado, *original;
  269.     char mod[40];
  270.     producto pro;
  271.     producto pro_mod;
  272.     visualizar("almacen.dat");
  273.     if((modificado=fopen("cambios.dat", "a+b"))==NULL || (original=fopen("almacen.dat", "r+b"))==NULL)
  274.     {
  275.         printf("No se pueden abrir los ficheros.\n");
  276.         exit(1);
  277.     }
  278.     printf("\n\n\Indique el CODIGO del producto del cual desea modificar los datos: ");
  279.     gets(mod); fflush(stdin);
  280.     while(fread(&pro, sizeof(producto), 1, original)!=NULL)
  281.     {
  282.       if(strcmp(mod,pro.codigo)==0)
  283.       {
  284.         printf("\nDescripcion: ");
  285.         gets(pro.descripcion);
  286.         fflush(stdin);
  287.         printf("\nPrecio: ");
  288.         scanf("%d", &pro.precio);
  289.         fflush(stdin);
  290.         printf("\nCantidad: ");
  291.         scanf("%d", &pro.cantidad);
  292.         fflush(stdin);
  293.         fwrite(&pro,sizeof(producto),1,modificado);
  294.       }
  295.     }
  296.     fclose(modificado);
  297.     fclose(original);
  298. }
  299.  
  300. void ordenar()
  301. {
  302.     FILE *original,  *temporal;
  303.     producto pro;
  304.     char **array;
  305.     char aux[5];
  306.     int i,j, cant_reg, total_reg;
  307.     if((original=fopen("almacen.dat", "rb"))==NULL
  308.     || (temporal=fopen("temporal.dat", "a+b"))==NULL)
  309.     {
  310.         printf("No se pueden abrir los ficheros.\n");
  311.         exit(1);
  312.     }
  313.     //cant_reg tenemos que calcular cantidad de registros
  314.     //asignacion dinamica para array con el numero de registros
  315.     fseek(original,0L,SEEK_END);
  316.     total_reg=(int)ftell(original);
  317.     cant_reg=total_reg/sizeof(producto);
  318.     fseek(original,0L,SEEK_SET);
  319.     array=(char **)malloc(sizeof(char*)*5);
  320.     for (i=0;i<cant_reg ;i++)
  321.     {
  322.         array[i]=(char *)malloc(sizeof(char)*5);
  323.     }
  324.    i=0;
  325.     while(fread(&pro, sizeof(producto), 1, original)!=NULL)
  326.     {
  327.         strcpy(array[i++], pro.codigo);
  328.     }
  329.  
  330.     //ordenamos los codigos
  331.     for(i=0;i<(cant_reg);i++)
  332.     {
  333.         for (j=(cant_reg)-1;j>0;j--)
  334.         {
  335.             if(strcmp(array[j],array[j-1])&lt;0)
  336.             {
  337.                 strcpy(aux,array[j]);
  338.                 strcpy(array[j],array[j-1]);
  339.                 strcpy(array[j-1],aux);
  340.             }