Thread: Weird cin behavior

  1. #1
    Registered User
    Join Date
    Apr 2004
    Posts
    42

    Weird cin behavior

    Hi. I'm having trouble with this overloaded >> function.

    Code:
    //Uses iostream.h, ctype.h, stdlib.h, and constants TRUE and FALSE:
    istream& operator >>(istream& ins, Money& amount)
    {
        char one_char, decimal_point,
             digit1, digit2; //digits for the amount of cents
        long dollars;
        int cents,
            negative;//set to TRUE if input is negative.
    
        ins >> one_char;
        if (one_char == '-')
        {
            negative = TRUE;
            ins >> one_char; //read '$'
        }
        else
            negative = FALSE;
        //if input is legal, then one_char == '$'
    
        ins >> dollars >> decimal_point >> digit1 >> digit2;
        
    
        if ( one_char != '$' || decimal_point != '.'
             || !isdigit(digit1) || !isdigit(digit2) )
        {   
             cout << "first";
             cin.get();
             
            cin.get(one_char);
            cout << one_char;
            cin.get();
            cin.get();
            cin.get();
            cin.get();
            cin.get();
            cin.get();
            cout << "last";
            cin.get();
            cout << "Error illegal form for money input. Try again\n";
            system("PAUSE");
            exit(1);
        }
    
        cents = digit_to_int(digit1)*10 + digit_to_int(digit2);
    
        amount.all_cents = dollars*100 + cents;
        if (negative)
            amount.all_cents = -amount.all_cents;
    
        return ins;
    }
    This is code from my book(without the cin.gets of course), and my program compiles fine. I'm was trying to modify it so that the user can reenter input if he messes up, instead of using exit(1). I think i got it working for some input, but If i input like '1' and then 'a' or 'a' and then 'd'...basicly, if i enter a character as my second input, which i believe goes into the variable dollars, the program doesn't let me input the rest of the variables, skips every cin.get(), and goes straight for the exit(1). Why? Sorry if this is easy, but I can't figure it out. I know 'dollars' is a 'long int' variable, but my book does say you can store a letter in an int. (I don't want to, but this behavior is prevented from allowing the user to reenter inputs sometime.)

    Thanks. :\
    Last edited by Link_26; 06-25-2006 at 07:45 PM.

  2. #2
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    Once cin attempts to read a letter into an integer variable and fails, it sets a flag to indicate it has failed. You need to clear that flag before trying again, or every single attempt to read after that will fail.

    Generally, you would call cin.clear() to clear the flags and cin.ignore(some big number, '\n') to ignore any bad data leftover in the stream (maybe that's what you were trying to do with all the cin.get()'s).

  3. #3
    Registered User
    Join Date
    Apr 2004
    Posts
    42
    Ah, ok. So why did it fail, or does that always fail? I thought it was legal, but...


    Anyway, i was using the cin.get()'s to try to get the program to stop before exiting when i put in that bad input. I did write this though to clear the buffer...

    Code:
    void clrbuff(void)
    {
        char x;
        cin.get(x);
       
        while(x != '\n')
        {
            
            cin.get(x);
            
        }
        
    }
    ...which got caught in an infinite loop with that bad input. Is that function fine, even if there are integers, ect in the buffer, or should i just use cin.ignore?

  4. #4
    Devil's Advocate SlyMaelstrom's Avatar
    Join Date
    May 2004
    Location
    Out of scope
    Posts
    4,079
    No, you're not understanding...

    When you do something an istream doesn't like, it sets its fail bit true. This makes it unuseable until you call clear on the stream. Since it's unuseable, all calls to cin are ignored. That's why you get an infinite loop.

    This is the common practice after you get bad input.
    Code:
    #include <limits>
    
    void clear_cin() {
       std::cin.clear();
       std::cin.ignore(std::numeric_limits<streamsize>::max(),'\n');
    }
    Code:
    while(!(std::cin >> myInput;)) {
       clear_cin();
       std::cout << "Bad Input, please re-enter:";
    }
    ...or something of the likes.
    Last edited by SlyMaelstrom; 06-25-2006 at 09:07 PM.
    Sent from my iPadŽ

  5. #5
    Registered User
    Join Date
    Apr 2004
    Posts
    42
    Sorry i guess i should have worded it differently. I understand now that the stream fails and thus why my loop failed. I was just telling why i had those cin.get(), and asking if my clrbuff() was fine(when the stream hasn't failed). I hadn't known about that cin.ignore function. anyway thanks you two.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. cygwin sshd weird behavior
    By jEssYcAt in forum Tech Board
    Replies: 6
    Last Post: 05-19-2008, 02:05 PM
  2. really weird behavior, 16 bit asm w/masm
    By BobMcGee123 in forum A Brief History of Cprogramming.com
    Replies: 7
    Last Post: 12-01-2005, 06:45 PM
  3. Weird computer behavior
    By ober in forum Tech Board
    Replies: 14
    Last Post: 03-08-2005, 12:26 PM
  4. Weird Excel behavior
    By Govtcheez in forum Tech Board
    Replies: 1
    Last Post: 12-03-2004, 01:53 PM
  5. odd behavior of cin.getline when it follows cin
    By Unregistered in forum C++ Programming
    Replies: 2
    Last Post: 01-28-2002, 02:38 PM