Reading Input with std::cin and std::getline
You have already used std::cout to send data out to the terminal. std::cin is its counterpart and reads in data from the keyboard. Both are declared in the <iostream> header file, and both use a stream operator, but in opposite directions.
std::cout << "Hello"; // << sends data out to the screenstd::cin >> name; // >> pulls data in from the keyboardThe arrows point toward where the data is going. >> is called the extraction operator: it extracts data from the input stream and places it into the variable on the right. A stream, in this context, is simply a sequence of characters.
How cin works
Consider this program:
If you run this program, you’ll see it pause at std::cin >> name, waiting for you to type something and press Enter. cin reads whatever you typed into name and execution continues.
A few things worth noticing:
namehas to be declared before you can read into it. Here, we declare it asstd::string, which is a type for storing text (covered in detail in a later chapter).- On line 7, we intentionally don’t send a
\nto the output stream. So, when you run the code, you’ll see in the terminal that the cursor stays on the same line and you can type right after it. std::cin >>only reads up to the first whitespace. So, if you type “John Doe”, only “John” is stored innameand “ Doe” remains in the input buffer.cin >>ignores leading whitespace, so adding anothercin >>statement after line 8 would retrieve “Doe” just fine.
As the program only sees the complete input after you press Enter, you can always backspace and correct a typo before pressing Enter.
Reading different types
cin >> works with all the fundamental types you have seen.
For char, it reads exactly one non-whitespace character. For numeric types like int, if the user enters something non-numeric like abc, the read fails silently and the variable is left unchanged.
You can also chain >> in a single statement. cin reads them in order, treating any whitespace as the separator between values:
double length, width;std::cout << "Enter length and width: ";std::cin >> length >> width;The user can type 10.5 4.0 on one line, or press Enter between them. Either way works.
Reading full lines with std::getline
Unlike cin >>, std::getline reads everything up to the Enter key, including spaces:
Here, std::getline(std::cin, full_name) will read everything the user typed up to the newline character, discard the newline itself, and store everything else in full_name.
Mixing cin >> and getline
What do you think would happen if you use cin >> first and then use std::getline, as in the following code:
You’ll notice that the getline appears to have been skipped, but it really wasn’t. When the user types 25 and presses Enter, cin >> age reads 25 but leaves the newline character sitting in the buffer. std::getline then runs, sees that newline immediately and treats it as an empty line.
The fix is one extra call right after the cin >> read:
std::cin >> age;std::cin.ignore();std::getline(std::cin, city);std::cin.ignore() discards exactly one character from the buffer. So any time you switch from cin >> to getline, call cin.ignore() in between. You can try this by adding it on line 10 of the code above.