Dev - C++ - ...Problema con scanf...

   
Vista:

...Problema con scanf...

Publicado por Ronald (3 intervenciones) el 04/11/2007 02:19:52
Saludos...

Tengo un problema con el scanf bastante raro. Hice este ejemplo (c++) facil de entender que muestra el problema:

#include <stdio.h>
int main()
{
char letra;
int num;
do{
scanf("%d", &num);
if(num > 0)
printf("%s\n", "es mayor a cero");
else
printf("%s\n", "no es mayor a cero");
scanf("%c", &letra);
}while(letra != '*');
return 1;
}

Lo que hace, lee un numero y dice si es mayor que cero o no. A continuacion lee un caracter, si el caracter leido es asterisco * entonces se termina el programa, sino vuelve a leer un numero.

Bastante simple, pero los reto a que lo prueben y veran que luego de leer el caracter vuelve a imprimir "es mayor a cero" o "no es mayor a cero". Osea que para cada numero ingresado muestra dos veces si es mayor a cero o no.

Este comportamiento es el problema pues para mi oficio necesito que la cantidad de salidas sea exacto pues esta la almacena en un archivo y luego verificada por otro programa.

Este programa funciona sin problemas usando el iostream, asi:

#include <iostream>
int main()
{
char letra;
int num;
do{
std::cin >> num;
if(num > 0)
std::cout << "es mayor a cero\n";
else
std::cout << "es mayor a cero\n";
std::cin >> letra;
}while(letra != '*');
return 1;
}

Pero necesito usar scanf por sus funciones de formateado al igual que printf.

Bueno si es que alguien se ha topado con este problema y llego con la solucion por favor responder a este post.

Nos vemos...
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder

RE:...Problema con scanf...

Publicado por eduardo (26 intervenciones) el 04/11/2007 19:49:49
Eso no es raro pues es algo logico que el programa reaccione de esa manera
lo que sucede es lo siguiente:

scanf("%d", &num);
lee el numero y al pulsar enter el caracter '\n' queda en el bufer de entrada

continua...
scanf( "%c", &letra ); toma '\n' y continua con la sgte instruccion sin esperar el ingreso del caracter desde teclado ya que scanf() encontró '\n' en el bufer

}while(letra != '*'); esto es verdadero ya que '\n' != '*'

arriba de nuevo..
scanf("%d", &num);
aca te permite ingresar el numero lo que tu asumes ingresar caracter y por error ingresas un caracter con lo cual no se asigna nada a la variable num y esta sigue teniendo el valor anterior es por eso que se repite el mensaje

Para corregir eso limpia el bufer de entrada despues de leer num para q te permita leer letra.

#include <stdio.h>
int main()
{
char letra;
int num;
do{
printf( " Ingrese numero entero: " );
scanf( "%d", &num );
if(num > 0)
printf( " %s\n", "es mayor a cero" );
else
printf( " %s\n", "no es mayor a cero" );

fflush( stdin );
printf( " Pulse * para terminar: " );
scanf( "%c", &letra );
}while (letra != '*' );

return 1;
}
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:...Problema con scanf...

Publicado por Ronald (3 intervenciones) el 04/11/2007 23:22:18
Hola Eduardo.

La verdad tiene logica lo que tu dices. Habia leido sobre el buffer de la entrada estandar, pero no se me ocurrio como era que afectaba a mi codigo.

Intente exactamente lo que tu propones, pero el problema no se soluciona (letra sigue capturando el valor de '\n'). Ya lo comprobe ejecutando paso a paso y mirando el valor de letra.

Osea parece que no funciona el fflush(stdin). Lo has probado??

Nota: estoy utilizando el compilador gcc de linux... sera eso?

Bueno saludos...
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

una solucion

Publicado por Ronald (3 intervenciones) el 04/11/2007 23:35:31
Bueno como el fflush no funciona, una posible solucion seria leer dos veces un caracter. Ya se que no es una manera elegante de solucionar pero funciona.

El codigo quedaria asi:

#include <iostream>

int main()
{
char letra;
int num;
do{
scanf("%d", &num);
if(num > 0)
printf("%s\n", "es mayor a cero");
else
printf("%s\n", "no es mayor a cero");

fflush( stdin );
printf( " Pulse * para terminar: " );
scanf("%c", &letra);
scanf("%c", &letra); //<--esto aumente
}while(letra != '*');
return 1;
}

Alguna otra sugerencia??

Saludos...
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:una solucion

Publicado por Gonzalo (2 intervenciones) el 12/11/2007 08:32:34
#include <stdio.h>

int main()
{
char letra;
int num;

do{

scanf("%d", &num);
fflush( stdin );

if(num > 0)
printf("%s\n", "es mayor a cero");
else
printf("%s\n", "no es mayor a cero");

printf( " Pulse * para terminar: " );
scanf("%c", &letra);
fflush( stdin );

}while(letra != '*');

return 1;
}
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:una solucion

Publicado por Miguel Santos M. (1 intervención) el 09/09/2012 20:05:36
Es un problema con scanf() ademas que tiene ese inconveniente, no logras controlarlo en ocaciones una solución que algunos autores sugieren:

#include <stdlib.h>


float cato;
char buff[6];


cato=atof(gets(buff)); // tomo el valor como char y lo transforma a float
estan para la conversion atol, atoi, atof, esto es convierte del caracter (ascii) a long. integer, float, y te evitas problemas del \n.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar