elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.
 
Inicio Ayuda Buscar Ingresar Registrarse
29 Mayo 2012, 03:03  


Tema destacado: Entra al canal IRC oficial de #elhacker.net

+  Foro de elhacker.net
|-+  Programación
| |-+  Programación C/C++ (Moderadores: Eternal Idol, Littlehorse)
| | |-+  Se pierde el primer cin.getline en un analisis de casos
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: Se pierde el primer cin.getline en un analisis de casos  (Leído 336 veces)
eleon

Desconectado Desconectado

Mensajes: 56


Ver Perfil
Se pierde el primer cin.getline en un analisis de casos
« en: 2 Febrero 2012, 22:41 »

Holas:

Tengo un pequeño problemilla y es que dentro de un analisis de casos (switch) no se me ejecuta el primer cin.getline(). Ejemplo:

Código
switch (opcion)
       {
           case 1:
               while (pEA->pSiguiente != 0)
               {
                   pEA = pEA->pSiguiente;
               }
 
               pEA->pSiguiente = new agenda;
               pEA = pEA->pSiguiente;
 
               cout << "Introduzca el nombre: ";
               cin.getline (nuevoNombre, tamNombre); //Este cin.getline() no se ejecuta
               pEA->configurarNombre (&nuevoNombre[0]);
               cout << endl;
 
               cout << "Introduzca el correo: ";
               cin.getline (nuevoCorreo, tamCorreo);
               pEA->configurarCorreo (&nuevoCorreo[0]);
               cout << endl;
 
              ...

He probado quitando la parte de "Introduzca el nombre" para comprobar que no es un error sintáctico y lo que sucede es que no se ejecuta el cin.getline del correo, es decir, el primer cin.getline del "case" se omite. Lo mismo me sucede en "case 2: " etc.

Para corroborarlo he probado a poner antes del "Introduzca el nombre" un cin.getline(cadena_prueba, 30), y entonces si que se ejecuta correctamente el del nombre.

¿Alguno sabe por qué el primero siempre se omite?.

Gracias y saludos.


En línea

rir3760


Desconectado Desconectado

Mensajes: 382


Ver Perfil
Re: Se pierde el primer cin.getline en un analisis de casos
« Respuesta #1 en: 3 Febrero 2012, 00:40 »

En la gran mayoría de los casos el comportamiento que mencionas se debe a que, antes de la parte que se "salta", tienes una sentencia que lee un valor de la entrada estándar pero deja el '\n' en el bufer.

Por ejemplo:
Código
string palabra;
char linea[100];
 
// ...
 
cin >> palabra;
cin.getline(linea, 100); // Esto se "salta"

Supongo es eso pero, para estar seguros, lo mejor es revisar el código fuente completo.

Un saludo


En línea

The capacity to learn is a gift;
The ability to learn is a skill;
The willingness to learn is a choice.
--
Rebec of Ginaz
eleon

Desconectado Desconectado

Mensajes: 56


Ver Perfil
Re: Se pierde el primer cin.getline en un analisis de casos
« Respuesta #2 en: 3 Febrero 2012, 08:27 »

Gracias por responder, la única entrada que hay antes es esta:

Código
    while (opcion != 5)
   {
       opcion = 0;
       while (opcion < 1 || opcion > 5)
       {
           F_menu();
           cin >> opcion; //Primera entrada en todo el programa
           cout << endl;
       }
 
       switch (opcion)
       {
           case 1:
               while (pEA->pSiguiente != 0)
               {
                   pEA = pEA->pSiguiente;
               }
 
               pEA->pSiguiente = new agenda;
               pEA = pEA->pSiguiente;
 
               cout << "Introduzca el nombre: ";
               cin.getline (nuevoNombre, tamNombre); // Entrada suprimida
               pEA->configurarNombre (&nuevoNombre[0]);
               cout << endl;
 
               cout << "Introduzca el correo: ";
               cin.getline (nuevoCorreo, tamCorreo);
               pEA->configurarCorreo (&nuevoCorreo[0]);
               cout << endl;
...

¿Por qué mete un "\n" automáticamente en el buffer?, ¿y cuál sería la solución para evitarlo?.

EDITO: Por si ayuda te pongo el cuerpo del programa hasta donde se produce el error:

Código
int main ()
{
   USHORT opcion;
 
   agenda objeto;
   agenda *pEA = &objeto;
   USHORT numContactos = 0;
 
   char nuevoNombre [tamNombre];
   char nuevoCorreo [tamCorreo];
   ULONG nuevoTelefono = 0;
   ULONG nuevoMovil = 0;
 
   bool encontrado;
   char nombre [tamNombre];
   char correo [tamCorreo];
   char *pNombre = 0;
   char *pCorreo = 0;
   USHORT contador;
 
   int i, j;
 
   while (opcion != 5)
   {
       opcion = 0;
       while (opcion < 1 || opcion > 5)
       {
           F_menu();
           cin >> opcion;
           cout << endl;
       }
 
       switch (opcion)
       {
           case 1:
               while (pEA->pSiguiente != 0)
               {
                   pEA = pEA->pSiguiente;
               }
 
               pEA->pSiguiente = new agenda;
               pEA = pEA->pSiguiente;
 
               cout << "Introduzca el nombre: ";
               cin.getline (nuevoNombre, tamNombre);
               pEA->configurarNombre (&nuevoNombre[0]);
               cout << endl;
 
               cout << "Introduzca el correo: ";
               cin.getline (nuevoCorreo, tamCorreo);
               pEA->configurarCorreo (&nuevoCorreo[0]);
               cout << endl;
...

Una cosa en la que me acabo de fijar es en cómo inicializo las cadenas en el constructor de la clase; ¿es correcto de esta forma o quizá sea lo que produce el error?:

Código
agenda::agenda()
{
   char nombre = {'\0'};
   char correo = {'\0'};
   telefono = 0;
   movil = 0;
 
   pSiguiente = 0;
}

Un saludo.
« Última modificación: 3 Febrero 2012, 08:37 por eleon » En línea

rir3760


Desconectado Desconectado

Mensajes: 382


Ver Perfil
Re: Se pierde el primer cin.getline en un analisis de casos
« Respuesta #3 en: 3 Febrero 2012, 16:31 »

El comportamiento es normal. Cuando se ejecuta la sentencia:
Código
cin >> opcion;
Se toman los caracteres necesarios de la entrada estándar pero el '\n' se queda en el bufer.

A continuación se ejecuta:
Código
cin.getline (nuevoNombre, tamNombre);
Y esa función espera "cero o mas caracteres seguidos del avance de linea", como ese ya se encuentra en el bufer se toma y procesa como un linea vacía.

Soluciones hay varias: una es descartar el resto de la linea justo después de la primera sentencia, otra opción es utilizar getline para todas las lecturas junto con la clase "stringstream" para obtener los valores (hay varios ejemplos de ello en la base de datos de los foros).

Un saludo
En línea

The capacity to learn is a gift;
The ability to learn is a skill;
The willingness to learn is a choice.
--
Rebec of Ginaz
eleon

Desconectado Desconectado

Mensajes: 56


Ver Perfil
Re: Se pierde el primer cin.getline en un analisis de casos
« Respuesta #4 en: 3 Febrero 2012, 22:24 »

Gracias por tu tiempo, he optado por usar "cin.ignore(1);" después del cin.

Saludos.
En línea

rir3760


Desconectado Desconectado

Mensajes: 382


Ver Perfil
Re: Se pierde el primer cin.getline en un analisis de casos
« Respuesta #5 en: 4 Febrero 2012, 00:40 »

En tu caso eso funciona pero (casi) como un castillo de naipes. Para explicarlo mejor compila y ejecuta el programa. Cuando te pida la opción teclea:
Código:
123 {ENTER}
Eso es: 1, 2, 3, un espacio y la tecla {ENTER}.

Es por ello que se considera una mejor opción leer una linea almacenándola en un objeto de la clase "string" y a continuación "extraes" el numero mediante otro objeto de la clase "stringstream".

Un saludo
En línea

The capacity to learn is a gift;
The ability to learn is a skill;
The willingness to learn is a choice.
--
Rebec of Ginaz
Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

Mensajes similares
Asunto Iniciado por Respuestas Vistas Último mensaje
Gates pierde el primer lugar en la lista de los más ricos
Noticias
wolfbcn 0 212 Último mensaje 10 Octubre 2008, 20:56
por wolfbcn
cin.getline y cin.ignore(cin.rdbuf()->in_avail())
Programación C/C++
Eliptico 2 3,053 Último mensaje 21 Junio 2009, 23:24
por vertexSymphony
Ayuda con getline PLEASE!!!!
Programación C/C++
oscareto74 2 1,777 Último mensaje 13 Julio 2009, 18:27
por nahuelveronesi
cin.getline [OTRA DUDA] jeje « 1 2 »
Programación C/C++
.:BlackCoder:. 21 4,347 Último mensaje 21 Enero 2010, 19:45
por O-LLOS-O
getline()
Programación C/C++
Geek7 3 1,221 Último mensaje 29 Julio 2010, 20:52
por Geek7
Powered by SMF 1.1.16 | SMF © 2006-2008, Simple Machines