No overflow in cout

This is a discussion on No overflow in cout within the C++ Programming forums, part of the General Programming Boards category; I am a little confused on why I do not get an overflow when I use the the following code. ...

  1. #1
    Registered User
    Join Date
    Dec 2010
    Posts
    5

    No overflow in cout

    I am a little confused on why I do not get an overflow when I use the the following code.

    I am using testvar+1 as an expression in cout. This should cause an overflow but doesn't


    Code:
     #include<iostream>
    #include<cstdlib>
    #include<cmath>
    using namespace std;
    
    int main()
    {
    	 
    
    	short testvar=32767;
    	
    	cout<<"The contents of testvar is"<<testvar<<endl;
    	cout<<"The contents of testvar with one added is: "<<testvar+1<<endl;
    	
    	
    	system("pause");
    	return 0;
    }

    However

    The code below causes an overlow, with the variable testvar in cout.

    Code:
    #include<iostream>
    #include<cstdlib>
    #include<cmath>
    using namespace std;
    
    int main()
    {
    	 
    
    	short testvar=32767;
    	
    	cout<<"The contents of testvar is"<<testvar<<endl;
    	testvar+=1;
    	
    	cout<<"The contents of testvar with one added is: "<<testvar<<endl;
    	
    	
    	system("pause");
    	return 0;
    }
    Not sure I understand what the differences are between the two code segments. In both instances you are adding 1 to testvar which should cause an overflow.

  2. #2
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,185
    You probably believe testvar+1 is of type short. It is not. testvar is of type short, but 1 is of type int, and C++ will automatically promote the smaller datatype to the larger before doing arithmetic. I don't think there's a suffix you can use to mean short (like you can use "L" for long, for instance), but you can do an explicit cast:
    Code:
    testvar+(short)1

  3. #3
    Registered User
    Join Date
    Jun 2005
    Posts
    6,163
    The literal value, 1, is of type int. Therefore, when computing "testvar+1", testvar is promoted to be of type int, and then 1 is added. The result is of type int. If an int can hold a larger value than a short - which is typical of most modern compilers - there will be no overflow.

    Note also that, strictly speaking, overflowing a signed int type gives undefined behaviour.
    Right 98% of the time, and don't care about the other 3%.

  4. #4
    Registered User hk_mp5kpdw's Avatar
    Join Date
    Jan 2002
    Location
    Northern Virginia/Washington DC Metropolitan Area
    Posts
    3,793
    An example, just to beat a dead horse (this is done in Visual Studio 2008):
    Code:
    #include <iostream>
    #include <typeinfo>
    #include <limits>
    
    int main()
    {
        short test = std::numeric_limits<short>::max();
    
        // Output original value of test and its type
        std::cout << "test   is: " << test
                  << " and is of type " << typeid(test).name()
                  << std::endl;
    
        // Output temporary value (test+1) and its type
        std::cout << "test+1 is: " << test+1
                  << " and is of type " << typeid(test+1).name()
                  << std::endl;
    
        // Increment variable test and then display value
        ++test;
        std::cout << "test   is: " << test << std::endl;
    
        return 0;
    }
    Output is:
    Attached Images Attached Images  
    "Owners of dogs will have noticed that, if you provide them with food and water and shelter and affection, they will think you are god. Whereas owners of cats are compelled to realize that, if you provide them with food and water and shelter and affection, they draw the conclusion that they are gods."
    -Christopher Hitchens

  5. #5
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    21,310
    I suggest that you modify hk_mp5kpdw's example to add:
    Code:
    // Output temporary value (test+test) and its type
    std::cout << "test+1 is: " << test+test
              << " and is of type " << typeid(test+test).name()
              << std::endl;
    You should observe that the result is still of type int, even though both operands are of type short. The points made by tabstop and grumpy are generally valid, but the usual arithmetic conversions are such that integral promotions are performed on both operands of operator+ here. In fact this rule, not the fact that one of the operands in your original example was of type int, is the reason for the integral promotion that was observed.
    C + C++ Compiler: MinGW port of GCC
    Version Control System: Bazaar

    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  6. #6
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,046
    Note: tabstop was correct, there is no suffix for short literals. You may be interested in this: Literal UL
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  7. #7
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,185
    Quote Originally Posted by dwks View Post
    Note: tabstop was correct, there is no suffix for short literals. You may be interested in this: Literal UL
    I would guess that goes back to Laserlight's point that shorter types get automatically promoted whenever they appear in a statement anyway, so there's not much point in it anyway. (I guess if you really wanted one, you could do "short(1)".)

  8. #8
    Registered User
    Join Date
    Dec 2010
    Posts
    5

    Overflow with cout

    Thanks for the feedback. I didn't realize how the rule with short to int applies. Is this a valid line of code to get testvar to overflow?


    cout<<static_cast<short>(testvar+1)<<endl;

    Thanks

    Dante

  9. #9
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    21,310
    Quote Originally Posted by DanteXP
    Thanks for the feedback. I didn't realize how the rule with short to int applies. Is this a valid line of code to get testvar to overflow?


    cout<<static_cast<short>(testvar+1)<<endl;
    For one thing, you would not actually be getting "testvar to overflow", since testvar is not modified. Now, if the result of testvar+1 cannot fit into the range of short, the result of the cast would be implementation defined (and perhaps this is the overflow that you are looking for).
    C + C++ Compiler: MinGW port of GCC
    Version Control System: Bazaar

    Look up a C++ Reference and learn How To Ask Questions The Smart Way

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Travel Expenses-Weird Result
    By taj777 in forum C++ Programming
    Replies: 4
    Last Post: 04-06-2010, 02:23 PM
  2. Replies: 4
    Last Post: 03-15-2010, 10:26 AM
  3. class methods to cout stream
    By shintaro in forum C++ Programming
    Replies: 5
    Last Post: 11-11-2008, 06:27 PM
  4. How Does cout Work
    By jrahhali in forum C++ Programming
    Replies: 8
    Last Post: 08-25-2004, 03:19 PM
  5. FAQ cout
    By evilmonkey in forum FAQ Board
    Replies: 1
    Last Post: 10-07-2001, 11:32 AM

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21