Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: minette1988 en 7 Junio 2010, 15:44 pm



Título: buscar deuda mayor
Publicado por: minette1988 en 7 Junio 2010, 15:44 pm
Hola, tengo el siguiente ejercicio que pide los datos de los clientes y quiero hacer un subprograma que me busque la deuda mayor y la muestre por pantalla. Lo he intentado, pero no me sale, me da errores.

Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4.  
  5. #define LEE_CHAR(c)\
  6. c=getchar();\
  7. while((c=='\n') || (c==' ') || (c=='\t'))\
  8. c=getchar();
  9.  
  10. #define LEE_CAD(c,n) { int i=0; \
  11.                      c[i]=getchar();\
  12.     while((c[i]=='\n') || (c[i]=='\t')) c[i]=getchar();\
  13.     while ((c[i]!='\n') && (i < (n-1))){ \
  14.        i++;\
  15. c[i]=getchar(); }\
  16.     c[i]='\0'; }
  17.  
  18. #define TAM_NOMBRE 100
  19. #define TAM_DIR 100
  20. #define NUM_CLIENTES 10
  21. struct cliente{
  22. char nombre[TAM_NOMBRE];
  23.        char direccion[TAM_DIR];
  24.        double deuda;
  25. };
  26. int main(){
  27. void crear_fich();
  28.        void deuda_mayor();
  29.        char sel;
  30. FILE *pf; //Puntero a fichero
  31.  
  32.        /* Abre el fichero para trabajar con él en Lectura / Escritura */
  33.        if((pf = fopen("datos.dat", "wb+")) == NULL) {/*"rb+"*/
  34.           /* Si no existe, ejecuta el módulo que lo cree */
  35.   crear_fich();
  36.   /* Una vez creado lo habre en lectura/escritura */
  37.           if((pf = fopen("datos.dat", "rb+")) == NULL) {
  38. perror("Fichero no accesible");
  39.                exit(1);
  40.   }
  41.        }
  42.  
  43. do{
  44. printf("MENÚ\n----\n");
  45.  
  46. printf("1). Dar de alta un cliente.\n");
  47.                printf("2). Mostrar la deuda mayor.\n");
  48.                printf("3). salir y eliminar.\n");
  49.                printf("0). Salir\n\nOpción(0-2): ");
  50.  
  51. do{
  52. LEE_CHAR(sel);
  53. }while( (sel<'0') || (sel>'3') );
  54.  
  55. switch(sel){
  56. case '1':{
  57. crear_fich(pf);
  58.    /* Una vez creado lo abre en lectura/escritura */
  59.    if((pf = fopen("datos.dat", "rb+")) == NULL) {
  60. perror("Fichero no accesible");
  61.                 exit(2);
  62.    }
  63. break;}
  64.                                case '2':{ deuda_mayor(pf);
  65.                                        break;}
  66.                                case '3':{ fclose(pf); pf=NULL; remove("datos.dat"); sel= '0';
  67. break;}
  68.                } //switch
  69. }while(sel!='0');
  70.  
  71. exit(0);
  72. }//main()
  73. ////////////////////////////////////////
  74. void crear_fich(FILE* pf) {
  75.         struct cliente cli[NUM_CLIENTES];
  76.         int i=0;
  77.         char otro;
  78.  
  79. if((pf = fopen("datos.dat", "ab")) == NULL) {
  80. perror("Al crear el fichero de datos");
  81.                exit(2);
  82.         }
  83.  
  84.         /* Lectura de los ciclistas */
  85.         do {
  86.  
  87. cli[i].deuda = 0.0;
  88.                printf("Nombre: "); LEE_CAD(cli[i].nombre, TAM_NOMBRE);
  89.                printf("Dirección: "); LEE_CAD(cli[i].direccion, TAM_DIR);
  90.                printf("Deuda: "); scanf("%lf", &cli[i].deuda);
  91.                /*Escribe el cliente en el fichero */
  92.                fwrite(&cli, sizeof(struct cliente), 1, pf);
  93. printf("¿Otro? (s/n) ");
  94.                LEE_CHAR(otro);
  95.        }while((otro=='s') || (otro=='S'));
  96. if(fclose(pf) == EOF){
  97. printf("Error al cerrar el fichero, compruebe si hay información.\n");
  98.                exit(3);
  99.        }
  100. } /* crear_fich()*/
  101. //////////////////////////////////
  102. void deuda_mayor(FILE *pf){
  103.        struct cliente cli[NUM_CLIENTES];  
  104.        int i=0;
  105.        int deuda_mayor;
  106.        deuda_mayor=0;
  107.        for(i=0; i<NUM_CLIENTES; i++){
  108.            rewind(pf);
  109.            fread(&cli,sizeof(struct cliente),1,pf);
  110.            while(!feof(pf)){
  111.                for(i=1; i<NUM_CLIENTES; i++){
  112.                   if(cli[i].deuda > cli[deuda_mayor].deuda);
  113.                      deuda_mayor=i;
  114.                }
  115.            }
  116.            printf("%s %.2lf\n", cli[deuda_mayor].nombre,cli[deuda_mayor].deuda);
  117.        }
  118. }

Cuando le doy la opción 2 que es mostrar la deuda mayor no hace nada.






Título: Re: buscar deuda mayor
Publicado por: Littlehorse en 7 Junio 2010, 22:32 pm
No hagas triple post! usa el botón modificar. :D

No vi todo el codigo pero por el error, que es lo que intentas hacer con esto?

Código
  1.           if(cli.deuda > cli[deuda_mayor].deuda);
  2.              deuda_mayor=cli.deuda;

No declaraste cli como un arreglo de estructuras como para utilizar los indices de esa forma.

Saludos


Título: Re: buscar deuda mayor
Publicado por: Horricreu en 7 Junio 2010, 22:35 pm
No hagas triple post! usa el botón modificar. :D

No vi todo el codigo pero por el error, que es lo que intentas hacer con esto?

Código
  1.           if(cli.deuda > cli[deuda_mayor].deuda);
  2.              deuda_mayor=cli.deuda;

No declaraste cli como un arreglo de estructuras como para utilizar los indices de esa forma.

Saludos

¿Y el if() no está mal declarado? No sería:

Código
  1. if(cli.deuda > cli[deuda_mayor].deuda) deuda_mayor = cli.deuda;

o

Código
  1. if(cli.deuda > cli[deuda_mayor].deuda)
  2. {
  3. deuda_mayor = cli.deuda;
  4. }

Saludos :P


Título: Re: buscar deuda mayor
Publicado por: Littlehorse en 7 Junio 2010, 22:39 pm
Si! también tiene que modificar eso, no había visto el ";" sobrante.

Saludos!


Título: Re: buscar deuda mayor
Publicado por: Horricreu en 7 Junio 2010, 22:40 pm
Si! también tiene que modificar eso, no había visto el ";" sobrante.

Saludos!

Ok. Entendidos entonces, edito porque no quiero que se entienda que he querido faltar el respeto a Littlehorse (perdona una vez más).

Saludos :P


Título: Re: buscar deuda mayor
Publicado por: Littlehorse en 7 Junio 2010, 23:41 pm
Citar
Ok. De nada, supongo :xD

Gracias por mostrarme el ";" sobrante que no había visto, igualmente yo te respondí porque pensé que eras vos el que estaba haciendo una pregunta, si no, no hubiese dicho nada porque lo que habías dicho es correcto. Ten en cuenta que no soy yo quien puso el código inicial, pero en fin, no desvirtuemos mas el hilo.

Y por cierto, no te respondí el pm porque tenes el buzón lleno.

Saludos

Edit:

Todo bien EPI  :)


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 8 Junio 2010, 12:55 pm
Os he hecho caso y he modificado el ejercicio a ver si me lo podéis mirar, por favor, sigue dándome fallos.
Hoy tengo examen. Gracias.


Título: Re: buscar deuda mayor
Publicado por: nicolas_cof en 8 Junio 2010, 14:55 pm
Un error es que te falta declarar NUM_CLIENTES, que lo usas dentro de la funcion crear_fich()

Ademas si declaras un arreglo de estructura, dentro del do-while tu cli.deuda tendria que ser cli[i].deuda, cli[i]..., obviamente previamente habiendo declarado e inicializado la variable i

Error en lo siguiente, deuda_mayor debe ser declarado de tipo int.

Código:
double deuda_mayor = 0.0;
...
cli[deuda_mayor].nombre, ...

Salu10.


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 8 Junio 2010, 15:56 pm
He vuelto a modificarlo, he quitado NUM_CLIENTES y no entiendo por qué deuda_mayor tiene que ser int si me tiene que sacar la deuda más alta que es de tipo double.


Título: Re: buscar deuda mayor
Publicado por: nicolas_cof en 8 Junio 2010, 16:01 pm
Porque si te fijas bien a deuda_mayor lo estas usando como indicador de posicion (el cual debe ser de tipo int) en un arreglo que en este caso no lo tenes ya que a cli no lo declaras como un arreglo de estructura.

Salu10.


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 8 Junio 2010, 17:13 pm
He modificado lo de double deuda_mayor = 0.0 y he puesto int deuda_mayor=0, pero me da estos errores:
En la función ‘deuda_mayor’:
deuda_mayor.c:113: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:113: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:117: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:117: error: el valor indicado por el subíndice no es ni matriz ni puntero


Título: Re: buscar deuda mayor
Publicado por: nicolas_cof en 8 Junio 2010, 17:20 pm
Código:
int main()
{
void crear_fich();
void deuda_mayor();
...

Las declaraciones de las funciones se hacen fuera de la funcion main()

Cita de: minette1988
En la función ‘deuda_mayor’:
deuda_mayor.c:113: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:113: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:117: error: el valor indicado por el subíndice no es ni matriz ni puntero
deuda_mayor.c:117: error: el valor indicado por el subíndice no es ni matriz ni puntero

Esos errores son porque intentas acceder a cli como si fuera un arreglo de estructura y no lo tenes declarado como tal.

Código:
struct cliente cli;
...
cli[i].deuda
...

Otro error que te veo es que nunca inicializas la variable num_clientes sin embargo realizas una comparacion i < num_clientes

Salu10.


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 8 Junio 2010, 20:39 pm
Acabo de modificarlo, corriguiendo los errores que me has dicho, pero cuando le doy a la opción 2 que busca la deuda más alta y la muestra por pantalla no hace nada.


Título: Re: buscar deuda mayor
Publicado por: nicolas_cof en 9 Junio 2010, 15:46 pm
Cita de: minette1988
Sigue sin funcionarme. Ayudadme, por favor.

Hola minette1988, la verdad yo te recomendaria plantearte bien que queres hacer y cual seria la mejor manera de hacerlo.

A lo largo de varias correcciones que se le han hecho a tu codigo, se nota que careces de conocimiento de muchos conceptos basicos.

Siendote sincero y espero no ofenderte, tu codigo es un lindo lio.

Citar
Cuando haces un mal trabajo y nadie te lo dice quiere decir que se han rendido contigo. Cuando alguien te esta corrigiendo lo hacen porque quieren que lo hagas mejor.

No dudes en consultar cualquier duda que tengas, que para eso estamos...

Salu10.


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 10 Junio 2010, 12:00 pm
Hola, en la función deuda_mayor lo primero que hago es definir la estructura:
     struct cliente cli;
luego como me interesa buscar la deuda más alta declaro una variable llamada deuda_mayor de tipo int que será la posición en la que se encuentra. Hasta aquí bien ¿no?. La duda que tengo es esta: La variable deuda que tengo definida en el struct cliente, ¿la tengo que comparar con la variable deuda_mayor que se encuentra en la función deuda_mayor?, ¿la variable deuda tengo que volver a definirla en este módulo o no hace falta?


Título: Re: buscar deuda mayor
Publicado por: minette1988 en 10 Junio 2010, 13:33 pm
He hecho la siguiente modificación :

Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4.  
  5. #define LEE_CHAR(c)\
  6. c=getchar();\
  7. while((c=='\n') || (c==' ') || (c=='\t'))\
  8. c=getchar();
  9.  
  10. #define LEE_CAD(c,n) { int i=0; \
  11.                      c[i]=getchar();\
  12.     while((c[i]=='\n') || (c[i]=='\t')) c[i]=getchar();\
  13.     while ((c[i]!='\n') && (i < (n-1))){ \
  14.        i++;\
  15. c[i]=getchar(); }\
  16.     c[i]='\0'; }
  17.  
  18. #define TAM_NOMBRE 100
  19.  
  20.  
  21. struct cliente{
  22. char nombre[TAM_NOMBRE];
  23.        double deuda;
  24. };
  25. int main(){
  26.  void alta();
  27.  void mostrar_todo();
  28.  void deuda_mayor();
  29.  char op;
  30.  FILE * pf;
  31.  
  32.  if((pf = fopen("datos.dat", "wb")) == NULL) {/*"rb+"*/
  33.           /* Si no existe, ejecuta el módulo que lo cree */
  34.   alta();
  35.  
  36.      if((pf = fopen("clientes.dat", "rb")) == NULL) {
  37. perror("Fichero no accesible");
  38.                exit(1);
  39.      }
  40.  }
  41.  
  42.  do{
  43. printf("MENÚ\n----\n");
  44.  
  45. printf("1). Dar de alta un cliente.\n");
  46.                printf("2). Mostrar todo.\n");
  47.                printf("3). Deuda mayor.\n");
  48.                printf("4). salir y eliminar.\n");
  49.                printf("0). Salir\n\nOpción(0-4): ");
  50.  
  51.                do{
  52. LEE_CHAR(op);
  53. }while( (op < '0') || (op >'4') );
  54.  
  55. switch(op){
  56.                    case '1': alta(pf); break;
  57.                    case '2': mostrar_todo(pf); break;
  58.                    case '3': deuda_mayor(pf); break;
  59.                    case '4':{ fclose(pf); pf=NULL; remove("clientes.dat"); op= '0';
  60. break;}
  61. }
  62.  }while(op != '0');
  63.  
  64. exit(0);
  65. }//main()
  66. //////////////////////////////////////////////////////////          
  67. void alta(FILE *pf){
  68.      struct cliente cli;
  69.      int fin;
  70.  
  71.  if((pf = fopen("clientes.dat", "ab")) == NULL) {
  72. printf("Error al crear el fitxer\n");
  73. }
  74. else {
  75. fin = 1; /* Termina con fin == 0 */
  76.  
  77.  
  78. while ( fin ) {
  79. printf ("Nombre del cliente: ");
  80. LEE_CAD(cli.nombre,TAM_NOMBRE);
  81.                        printf ("Deuda: ");
  82.                        scanf("%lf",&cli.deuda);
  83. fwrite(&cli,1,sizeof cli,pf);
  84. printf("Otro (0--> NO, 1--> SI)? ");
  85. scanf("%d",&fin);
  86. }
  87. if (fclose(pf))
  88. printf("Error al guardar el fichero\n");
  89. }
  90. }
  91. /////////////////////////////////////////////
  92. void mostrar_todo(FILE *pf){
  93.       struct cliente cli;
  94.  
  95.       if((pf = fopen("clientes.dat", "rb")) == NULL) {
  96. printf("Error al abrir el fichero clientes.dat\n");
  97.       }
  98.       else{
  99.  
  100. fread(&cli, 1, sizeof cli, pf);
  101.        while (!feof(pf)){
  102. printf("%s  %.2lf\n", cli.nombre, cli.deuda);
  103. fread(&cli,1, sizeof cli,pf);
  104.        }
  105.        fclose(pf);
  106.  }
  107. }
  108. //////////////////////////////////
  109. void deuda_mayor(FILE * pf){
  110.        struct cliente max,cli;
  111.  
  112.        if((pf = fopen("clientes.dat", "rb")) == NULL) {
  113. printf("Error al abrir el fichero clientes.dat\n");
  114.        }
  115.        else{
  116.             fread(&max,1,sizeof cli,pf);/*supongo que el primero es el mayor*/
  117.             while(!feof(pf)){
  118.                if(cli.deuda > max.deuda)/*si es mayor que el actual lo cambia*/
  119.                   max=cli;
  120.                fread(&cli,1,sizeof cli,pf);
  121.             }
  122.        }
  123.        fclose(pf);
  124.        printf("%s %.2lf\n",cli.nombre,cli.deuda);
  125. }

Cuando lo compilo introduzco los datos de 2 clientes: Si la deuda del primero es mayor que la del segundo me muestra la del segundo que es la más pequeña, sin embargo si la deuda del segundo es mayor que la del primero me muestra ésta última. ¿Dónde está el fallo? Ayudadme, por favor, el martes tengo recuperación. Gracias.