Thread: testing for int or float

  1. #1
    Registered User
    Join Date
    Aug 2005
    Posts
    266

    testing for int or float

    whats the best way to test user input to see if it is a whole number?
    for example , i want to force whole number input only

    and another question on the side,, is there a isDigit() function for strings, or is it only for char
    Last edited by rodrigorules; 11-22-2007 at 09:36 PM.

  2. #2
    Registered User
    Join Date
    Aug 2007
    Posts
    18
    maybe,

    Code:
    if((float)variable)
    {
       cout << "you entered an invalid number, try again: ";
       cin  >> variable;
    }
    I could be wrong.

  3. #3
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    would (float)variable, return true/false?

    (i just tried it, and it takes all input and returns it as True for some reason)
    im saving input in a Float data type btw
    Last edited by rodrigorules; 11-22-2007 at 09:43 PM.

  4. #4
    Registered User
    Join Date
    Nov 2007
    Location
    void
    Posts
    3
    Use int instead of float (a float means it can have decimal)

  5. #5
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    heres my code snippit

    Code:
    void over(float* end);
    
    int main()
    {
        float* ender;
        int num;
        do{
             cout << "When does sequence end (1+..1/n), Enter a number, (whole)? ";
             cin >> num;
             cout << endl;
        }while(num <1 || (float)num); 
        float core = float(num);
        ender = &core;
        over(ender);
        cout <<"Sequence ends at " << core;
    }
    entering any whole number makes it ask me again,,, entering a floating digit number makes it send a never ending amount of lines!
    Last edited by rodrigorules; 11-22-2007 at 09:59 PM.

  6. #6
    and the hat of sweating
    Join Date
    Aug 2007
    Location
    Toronto, ON
    Posts
    3,545
    Quote Originally Posted by rodrigorules View Post
    heres my code snippit

    Code:
    void over(float* end);
    
    int main()
    {
        float* ender;
        int num;
        do{
             cout << "When does sequence end (1+..1/n), Enter a number, (whole)? ";
             cin >> num;
             cout << endl;
        }while(num <1 || (float)num); 
        float core = float(num);
        ender = &core;
        over(ender);
        cout <<"Sequence ends at " << core;
    }
    entering any whole number makes it ask me again,,, entering a floating digit number makes it send a never ending amount of lines!
    (float)num is pointless since num is an int.

    What's happening here is that cin is expecting an int, but it's getting something else, which causes it to set the failbit flag, plus the data the user entered is still in the input stream, so when the loop comes back to cin again it sees the same data as before and immediately moves to the next statement...

    Oh, and here's an FAQ on exactly what I just pointed out: http://faq.cprogramming.com/cgi-bin/...&id=1043284392

  7. #7
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    heres what the tutorial says
    Code:
    int main()
    {
      int input;
    
      std::cout<<"Enter a number: ";
      
      while ( !( std::cin>> input ) ) {
        // Clear the error state
        std::cin.clear();
    
        // Remove the unrecognized characters
        std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
    
        // Try again
        std::cout<<"Invalid input. Please try again: ";
      }
      
      std::cout<<"You entered "<< input <<'\n';
    }
    can you explain to me what
    Code:
    while ( !( std::cin>> input ) )
    does?

    and im new to c++ and i don't understand what using double colon does.. ::
    i see that they didnt type 'using namespace std' at the top so im assuming thats how you apply a namespace manually, i guess...but whats a namespace anyway, lol

    thanks, this will be a great help to me since this is a common problem i run into
    Last edited by rodrigorules; 11-23-2007 at 12:02 AM.

  8. #8
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    Code:
    std::cin>> input
    This does the input. It reads an integer into the input variable. It returns a value that evaluates to true if cin was able to read in an int. If it does not read an int, it will evaluate to false. That means that
    Code:
    while ( !(std::cin >> input))
    will loop while cin is unable to read in an int.

    When the read fails, it sets the failbit. You need to call cin.clear() to clear that failbit so cin can read again. The cin.ignore() part ignores the invalid input.

    Now, there's a problem, though. You want the input to fail if the user types something with a decimal, right? So if they type 3.5, it should fail. But the code from the FAQ will successfully read in the 3 into input and leave the .5 in the input stream.

    A simple remedy is to check to see if the next character is a newline after the int is read. If the user types 3 and hits enter, the input stream will be '3', '\n'. If they type 3.5, it will be '3', '.', '5', '\n'. So when the user enters bad input the next character will not be a '\n'. With that change the example looks like this:
    Code:
    #include <iostream>
    #include <limits>
    #include <ios>
    
    int main()
    {
      int input;
    
      std::cout<<"Enter a number: ";
      
      while ( !( std::cin>> input ) || std::cin.get() != '\n' ) {
        // Clear the error state
        std::cin.clear();
    
        // Remove the unrecognized characters
        std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
    
        // Try again
        std::cout<<"Invalid input. Please try again: ";
      }
      
      std::cout<<"You entered "<< input <<'\n';
    }
    Note that the call to get() will remove the newline, which is actually good, because it can cause strange issues later on.

  9. #9
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    i am confused a bit, why does checking for a newline help check if its a whole number

    is there any way to read the cin stream to check for decimal, so i can see if a whole number wasnt entered?
    (even though the decimal part would be left in the stream, i would still like to test for it [to learn])
    Last edited by rodrigorules; 11-23-2007 at 12:32 AM.

  10. #10
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    Because the only way for somebody to enter a decimal is to type the decimal point. Since you are reading in an int, cin will stop at the decimal point automatically.

    So whether the user types 3 or 3.5, cin will still read in the value 3 into the variable. To tell the difference, you just need to check the next character.

    If the user types 3 by itself, the next character will be a newline (from when they hit enter). If the user types 3.5 the next character will be a period. If the user types 3abc, the next character will be an 'a'. You want the read to fail if the user types 3.5 or 3abc, so all you have to do is check to see if the next character is not the newline.

  11. #11
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    Code:
    while ( !( std::cin>> input ) || std::cin.get() != '\n' )
    this doesn't check for what you described right? or does it ?

    edit: nvm i tested it..it does in fact work
    how does it know that i entered a decimal or letter though?
    Last edited by rodrigorules; 11-23-2007 at 12:37 AM.

  12. #12
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    Yes, it does. The first have reads the number (3 in my example). The second have calls get() which gets a single character, which will be the next character in the stream. If that character is not a newline then the input was bad and the control enters the loop to clean up and tell the user they entered bad input.

  13. #13
    Registered User
    Join Date
    Aug 2005
    Posts
    266
    so this method relys that we are using an int, if it were something else cin wouldn't stop after the first numbers

  14. #14
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    cin keeps reading characters as long as they don't make the input fail. Once it reaches a character that isn't allowed to be a part of the type it is reading, it stops.

    So for an int, only digits are allowed. Any non-digit will stop the input. For a floating point type like double or float, a single decimal point is allowed, so it will keep going even if it finds a decimal point.

  15. #15
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Read the whole line into a std::string using getline.
    Attempt to find a "." in the string, if none is found, it might still be an integer.
    Then attempt to convert that string into an integer (using any method you like).
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 2
    Last Post: 05-13-2009, 03:25 PM
  2. Replies: 14
    Last Post: 06-28-2006, 01:58 AM
  3. Could somebody please help me with this C program
    By brett73 in forum C Programming
    Replies: 6
    Last Post: 11-25-2004, 02:19 AM
  4. Half-life SDK, where are the constants?
    By bennyandthejets in forum Game Programming
    Replies: 29
    Last Post: 08-25-2003, 11:58 AM
  5. How do you search & sort an array?
    By sketchit in forum C Programming
    Replies: 30
    Last Post: 11-03-2001, 05:26 PM