Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: foreground en 30 Septiembre 2012, 21:25 pm



Título: Duda con ejercicio de clase
Publicado por: foreground en 30 Septiembre 2012, 21:25 pm
Buenas noches! En fin el caso es que llevo un cacao impresionante con la asignatura de Porgramación I de ingeniería industrial. El ejercicio que tenía que realizar en cuestión era un pequeño programa que contara las letras "z" y "Z" de un archivo llamado prueba.txt

El tema está en que si el archivo está en blanco me devuelve que hay 0 Z pero si pongo cualquier otro carácter dentro del archivo al leerlo el programa se cuelga. No me ha dado ningún error al compilarlo pero me imagino que estaré haciendo una burrada así que espero que me ayuden. Este es el código en cuestión

Código
  1. #include<stdio.h>
  2. #include<stdlib.h>
  3.  
  4. int main()
  5. {FILE *f;
  6. FILE *s;
  7. int x=0;
  8. char c;
  9. f=fopen("prueba.txt","r");
  10. if(f==NULL){printf("error al encontrar el archivo\n");
  11. fclose (f);
  12. }
  13. else {while(fscanf(f,"%c",c)!=EOF) if((c='z')||(c='Z'))
  14. x++;
  15. }
  16. fclose(f);
  17.  
  18. printf("hay %d z\n",x);
  19. system("PAUSE");
  20. return 0;
  21. }


Título: Re: Duda con ejercicio de clase
Publicado por: Caster en 30 Septiembre 2012, 21:53 pm
No se nada sobre ficheros y ese tema, pero te digo que si eso solo te pasa cuando hay algo escrito el problema estará a partir del else. Yo creo que el fallo está dentro del bucle while, pero no se.

Saludos


Título: Re: Duda con ejercicio de clase
Publicado por: xiruko en 30 Septiembre 2012, 23:24 pm
he intentado seguir tu codigo pero he desistido a los pocos segundos... tanto para ti como para alguien que tenga que leer tu codigo, el orden y ser minucioso es algo que se agradece muchisimo. aqui te dejo el code que funciona, ya que tu has aportado tu parte y seguramente el error estuviera en alguna llave que te hayas dejado o algun parentesis. lo he hecho con la funcion fread() en lugar de fscanf(), ya que me gusta mas comparar con caracteres leidos que no con EOF (es algo personal y no por ello mejor o peor), pero bueno al menos tienes un code funcional y asi puedes mirar que es lo que sucede en el tuyo.

Código
  1. #include <stdio.h>
  2.  
  3. int main()
  4. {
  5. FILE *f=NULL;
  6. int numeroZ=0, bytesLeidos;
  7. char c;
  8.  
  9. f=fopen("prueba.txt","r");
  10. if (!f) {
  11. printf("Error: No se pudo abrir el archivo.\n");
  12. return 1;
  13. }
  14.  
  15. do {
  16.  
  17. bytesLeidos=fread(&c, sizeof(char), 1, f);
  18. if (c=='z' || c=='Z') numeroZ++;
  19.  
  20. } while (bytesLeidos>0);
  21.  
  22. fclose(f);
  23. printf("Numero de 'z' y 'Z': %d\nPulsa enter para salir...", numeroZ);
  24.  
  25. return 0;
  26. }

por cierto, es muy pesado hacer una llamada al sistema para pausar el programa. en lugar de ello, con un simple getchar() se consigue el mismo efecto.

un saludo!

edito: donde estudias ingenieria industrial? yo la hago en barcelona y aun me acuerdo de lo TOSTon que era... xD


Título: Re: Duda con ejercicio de clase
Publicado por: leosansan en 1 Octubre 2012, 00:29 am
....era un pequeño programa que contara las letras "z" y "Z" de un archivo llamado prueba.txt....

Citar
Y por qué no e y E o s y S ...... para no alterar el código mucho, entro las letras a contar en los "define", así si te pide otro juego de letras sólo tendrás que cambiar dichos define. Para que veas que funciona te "creo"y escribo  el fichero con dos líneas -los "fputs"-. Espero te sea de ayuda:

Código
  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. #define letra  'o'
  4. #define LETRA  'O'
  5. int main()
  6. {
  7.    FILE *fichero;
  8.    int nletra=0;
  9.    char c;
  10.    fichero=fopen("prueba.txt","w");
  11.    if(fichero==NULL)
  12.        {
  13.            printf("error al buscar el archivo\n");
  14.            return 1;
  15.        }
  16.    fputs("Esto es una linea\n", fichero);
  17.    fputs("Esto es otra y estO es continuacion de lo anterior", fichero);
  18.    fclose (fichero);
  19.    fichero=fopen("prueba.txt","r");
  20.    do {
  21.      c = getc (fichero);
  22.      if (c == letra || c == LETRA) nletra++;
  23.    } while (c != EOF);
  24.    fclose (fichero);
  25.    printf("Numero de '%c' y '%c': %d",letra,LETRA, nletra);
  26.    printf ("\nPresiona ENTER para salir:");
  27.    while (getchar()!='\n')
  28.            ;
  29.    return 0;
  30. }


Título: Re: Duda con ejercicio de clase
Publicado por: xiruko en 1 Octubre 2012, 00:51 am
Código
  1. while (getchar()!='\n')
  2.            ;

una pregunta... por que ultimamente poneis por aqui esto de esta manera? y no como cualquier otra sentencia:

Código
  1. while (getchar()!='\n');

ademas que eso no es para pausar el programa aunque lo haga, sino que eso se utiliza para vaciar el bufer de entrada stdin despues de haber usado scanf para leer algun entero por ejemplo. si este fuera el caso, tu programa no se pausaria ya que quedaria seguro un \n en stdin y por lo tanto no se haria la pausa.

realmente eso se usa para limpiar el bufer de entrada, y luego simplemente con un getchar() se pausa el programa a la espera de que el usuario presione enter.

pero bueno que mi post simplemente es por el ";" puesto de esa manera, ya que intento ser bastante minucioso y no se por que lo poneis asi xD

un saludo!


Título: Re: Duda con ejercicio de clase
Publicado por: rir3760 en 1 Octubre 2012, 03:25 am
No me ha dado ningún error al compilarlo pero me imagino que estaré haciendo una burrada así que espero que me ayuden.
Los errores son dos y se encuentran en el bloque "else" del condicional, estos son la falta del operador '&' en la llamada a "fscanf" y el uso del operador de asignación '=' cuando debería ser el de comparación "==". Esa parte con las correcciones:
Código
  1. }else {
  2.   while (fscanf(f, "%c", &c) != EOF)
  3.      if ((c == 'z') || (c == 'Z'))
  4.         x++;
  5. }

Ademas declaras dos variables de tipo "FILE *" cuando solo necesitas una, puedes eliminar la variable "s" sin problemas.


En cuanto al programa de leosansan hay que tener cuidado cuando se utilizan las funciones "getchar", "fgetc" y "getc" ya que su tipo de retorno no es "char", es "signed int". Ello porque esas funciones deben retornar el carácter (puede ser cualquiera) mas un valor único para indicar el estado de fin de archivo (EOF).

En buen cristiano hay que cambiar el tipo de la variable "c", mas o menos así:
Código
  1. int c;
  2.  
  3. /* ... */
  4.  
  5. while ((c = getc(fichero)) != EOF)
  6.   if (c == letra || c == LETRA)
  7.      nletra++;

Un saludo


Título: Re: Duda con ejercicio de clase
Publicado por: Caster en 1 Octubre 2012, 07:02 am
Código
  1. while (getchar()!='\n')
  2.            ;

una pregunta... por que ultimamente poneis por aqui esto de esta manera? y no como cualquier otra sentencia:

Código
  1. while (getchar()!='\n');

ademas que eso no es para pausar el programa aunque lo haga, sino que eso se utiliza para vaciar el bufer de entrada stdin despues de haber usado scanf para leer algun entero por ejemplo. si este fuera el caso, tu programa no se pausaria ya que quedaria seguro un \n en stdin y por lo tanto no se haria la pausa.

realmente eso se usa para limpiar el bufer de entrada, y luego simplemente con un getchar() se pausa el programa a la espera de que el usuario presione enter.

pero bueno que mi post simplemente es por el ";" puesto de esa manera, ya que intento ser bastante minucioso y no se por que lo poneis asi xD

un saludo!

Pues realmente da igual como ponerlo, el resultado será el mismo, y ya se ha explicado en otros post y varias veces además, la función de ese bucle, ya se sabe que es para limpiar el buffer.

Saludos