C/C ++ misunderstanding 3: fflush (stdin)

Source: Internet
Author: User

1.Why? Fflush (stdin)Yes

 

First, check the following program:

 

# Include<Stdio. h>

 

Int main (void)

{

Int I;

For (;;){

Fputs ("Please input an integer:", stdout );

Scanf ("% d", & I );

Printf ("% d/N", I );

}

Return 0;

}

 

This program will first prompt the user to enter an integer, and then wait for the user to input. If the user inputs an integer, the program will output the integer just entered and prompt the user to enter an integer again, then wait for user input. However, once the user does not enter an integer (such as a decimal or letter), assumeScanfIf the last integer obtained by the function is 2, the program will continuously output "Please input an integer: 2 ". This is becauseScanf ("% d", & I );Only integers are allowed. If you enter a letter, the letter will be left in"Input buffer. BecauseBufferThere is data, soScanfThe function will not wait for user input, but read it directly in the buffer, but it is a letter in the buffer, and this letter is left in the buffer again, so repeatedly, as a result, "Please input an integer: 2" is output continuously ".

 

Someone may say, "this is the case. Add 'fflush (Stdin); ', SetInput bufferJust clear it ?" However, this is wrong!CAndC ++OfStandardFflush (stdin) has never been defined in ). Some people may say, "but I used fflush (stdin) to solve this problem. How can you say it is wrong ?" Indeed,SomeCompiler (suchVc6) Supports the use of fflush (stdin) to clear the input buffer, but not all compilers must support this function (LinuxGccNot Supported), because fflush (stdin) is not defined in the standard ).MsdnThe document also clearly states that fflush on input stream isExtensionTo the c Standard (fflush operation input stream is standard for CExpansion). Of course, if you don't care about the programPortability, Fflush (stdin) is no big problem. Below isC99PairFflushFunction Definition:

 

Int fflush (File*Stream);

 

IfIf the most recent operation executed by stream is not input, the fflush function transfers any data to be written in the stream
Host environment writes data to a file. Otherwise, its behavior isUndefined.

The original article is as follows:PointOutput streamOrUpdate stream(Update stream), and the update stream


Int fflush (File*Stream);

If stream points to an output stream or an update stream in which
The most recent operation was not input, the fflush function causes
Any unwritten data for that stream to be delivered to the host environment
To be written to the file; otherwise, the behavior is undefined.

 

The host environment can be understood as the operating system or kernel.

 

From this we can see that if stream points to the input stream (such as stdin), then the behavior of the fflush function is uncertain. ThereforeFflush (stdin)Is incorrect, at least YesPoor portability.

 

2.ClearInput bufferMethod

 

Although fflush (stdin) cannot be used, we can write code to clear it.Input buffer. You only need to add a few simple codes after the scanf function.

/* C version */
# Include<Stdio. h> 


Int main (void)
{
Int I, C;
For (;;)
{
Fputs ("Please input an integer:", stdout );
Scanf ("% d", & I );

If (feof (stdin) | ferror (stdin ))
{/* If the user inputsEnd mark(Or the file has beenRead),*/
/* Or occursRead/write errors, Then exit the loop */

/* Do something */
Break;
}
/* If no error occurs, clear the input stream. */
/* Use the while loopInput stream"Eat" the remaining data in */
While (C = getchar ())! = '/N' & C! = EOF );
/* UseScanf ("% * [^/n]");You can also clear the input stream ,*/

/* Will remain/NCharacter. */

Printf ("% d/N", I );
}

Return 0;
}

/* C ++ version */
# Include<Iostream>
# Include<Limits>// To use numeric_limits
Using STD: cout;
Using STD: Endl;
Using STD: CIN;
Using STD: numeric_limits;
Using STD: streamsize;
Int main ()
{
Int value;
For (;;)
{
Cout <"enter an integer :";
Cin> value;
If (CIN. EOF () | cin. Bad ())
{// If the user inputsEnd mark(Or the file has beenRead),
// Or occursRead/write errorsTo exit the loop.

// Do something
Break;
}
// When an invalid character is read, the input stream will be inError status,
// To continue obtaining input, call the clear function first.
// ComeClear error mark of input streamBefore calling
// Ignore function to clear data in the input stream.
Cin. Clear ();
// Numeric_limits<Streamsize>: Max () returns the size of the input buffer.
// The ignore function clears the data in the input stream.
// You can query the specific usage of these two functions by yourself.
Cin. Ignore (numeric_limits<Streamsize>: Max (), '/N ');

Cout <value <'/N ';
}

Return 0;
}

References:

ISO/IEC 9899: 1999 (E) programming ages-C 7.19.5.2 the fflush Function

The C programming language 2nd edition by kernighan & Ritchie

ISO/IEC 14882 () programming languages ages-C ++

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.