cin.get() function not preventing command prompt closer

Dear Users,

I've seen a lot of beginners asking how to prevent the command prompt from closing. Some of the answers are dangerous (i.e. system(pause)) as pointed out by more seasoned programmers. Some are much more complicated that a beginner can understand. However, I found a potential solution, but I would like the input from more experienced programmers to prevent unintended consequences.

Some have suggested using the function cin.get(), cin being an object of class istream which, when added to the end of a program, waits until the user inputs a character. This function is usually inserted immediately before "return 0" at the end of the program. However, this method does not work if you previously use the object cin somewhere else in your program to read input from the user.

I think this happens because what the user input using cin is not flushed from the buffer or stream. Therefore, when you reach the cin.get() function at the end of your program, the function already has something to "get" and it executes the function. It doesn't have to wait. Therefore, your command prompt closes immediately.

The way I circumvented this problem is to use the cin.ignore(); function immediately before the cin.get() function. The cin.ignore() function extracts and ignores characters from the input object cin. I think this cleans out the stream or buffer, and prevents the cin.get() function from executing. Then, it simply waits for a new input from the user.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include <iostream>
using namespace std;

int main ()
{
	// Initialize the variables for memory storage.
	int low, high;

	// Ask the user for two integers and store them.
	cout << "Please type two integer numbers see which numbers are between them." << endl;
	cin >> low >> high;

	// Use a loop to print each number between the two integers.
	while (low <= high){
		cout << "Count = " << low << endl;
		++low;
	}

        // Ignores previous inputs and waits for a new input before closing.
	cin.ignore();
	cin.get();
	return 0;
}


The question is: Are there unintended consequences to this approach that I don't understand yet?
You have the right idea.

My only comment is that by calling cin.ignore() with default arguments, you will only ignore a single character in the input buffer. If there is more than one character remaining in the input buffer, the cin.get() will return immediately.
@ AbstractionAnon

Is there a way to ignore or clear everything in the input buffer?

From Cplusplus reference, it seems like the cin.ignore() function does clear multiple characters, not just one. Am I reading this wrong?

Extracts characters from the input sequence and discards them, until either n characters have been extracted, or one compares equal to delim.

The function also stops extracting characters if the end-of-file is reached. If this is reached prematurely (before either extracting n characters or finding delim), the function sets the eofbit flag.

Internally, the function accesses the input sequence by first constructing a sentry object (with noskipws set to true). Then (if good), it extracts characters from its associated stream buffer object as if calling its member functions sbumpc or sgetc, and finally destroys the sentry object before returning.
Last edited on
it seems like the cin.ignore() function does clear multiple characters, not just one
It can discard multiple characters if you would say so. Say, what is n value in "until either n characters"?

Best solution to this problem is no solution. Most real-world command line application do not have pause at the end.
If you are using IDE: config your IDE. Visual Studio users: launch your projects without debugging (Ctrl+F5 hotkey).
If you are not using any IDE: why do you have this problem? You are supposed to launch those programs from command line.
Extracts characters from the input sequence and discards them, until either n characters have been extracted...

The default value of n is 1.
http://www.cplusplus.com/reference/istream/istream/ignore/

 
istream& ignore (streamsize n = 1, int delim = EOF);

Last edited on
@ Duoas

I read through the first link, and while I trust the integrity of the code, I don't understand even a quarter of it. I wouldn't be able to replicate it myself. I also read through the second link and looked up some additional references. That I do understand, and it seems to be very similar to my initial approach, but adds some specificity, which I like.

Do you have a preference on which one you use?
Last edited on
I know that a beginner won't understand even the half of it. (Even the stuff he/she thinks he/she does understand.) That's part of the reason I just crunched it down into a little square block of text. It's a black box.

I write my programs such that they don't need to PAUSE.
@ Duoas & AbstractionAnon & MiiNiPaa

Thank you everybody for your feedback. It is starting to make a lot more sense now. All three of you have hit on the same thing, that the default value for n is 1. Duoas gave a link to the following code which reads the max number of characters stored in the input buffer and then ignores that same number and waits to close:

1
2
3
4
5
...
cout << "Press ENTER to close..." << endl;
	cin.ignore( numeric_limits<streamsize>::max(), '\n' );
	return 0;
}


However, I have found this same approach doesn't work for all situations. It is very dependent on what one has written in the code previously. For example, the following code does not wait for the user to hit enter:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#include <iostream>
using namespace std;

int main ()
{
	// Initialize Variables
	int currVal, val, cnt = 1;

	// Reads in the variables and checks each one thereafter
	if (cin >> currVal){
		while (cin >> val){
			if (val == currVal){
				++cnt;}
			else {
				cout << currVal << " occurs " << cnt << " times. " << endl;
				currVal = val;
				cnt = 1;
			}
		}
	}

	// Prompts user to hit ENTER to close the program.
	// Reads the input buffer, finds the max size in the buffer, and discards all of it.
	// Waits for user to hit ENTER before closing the command prompt.
	cout << "Press ENTER to close..." << endl;
	cin.ignore( numeric_limits<streamsize>::max(), '\n' );
	return 0;
}


I then tried MiiNiPaa's idea of just using the "Start without Debugging" command in my Visual Studio, but no window actually pops up! Either that or it pops up and then disappears so quickly I can't tell. My code is the following:

1
2
3
4
5
6
7
8
#include <iostream>
using namespace std;

int main ()
{
	cout << "Hey there!" << endl;
	return 0;
}


Update!

For those working with IDE Microsoft Visual Studio, I found this:
If you have a C++ app and Run Without Debugging and the console window still closes, you need to remember to explicitly set the Subsystem to Console under Configuration Properties / Linker / System. This can happen if you start with an Empty Project, which leaves Subsystem unset. – Trevor Robinson Aug 25 '10 at 18:39

I tried this and it seems to work great! Thank you MiiNiPaa!

The pathway to find the subsystem is the following:
Project > Properties > Configuration Properties > Linker > System, change Subsystem to "Console"
Last edited on
Topic archived. No new replies allowed.