I'm trying to store the input that user enters through console. so I need to include the "enter" and any white space.
But cin stops giving me input after the first space.
Is there a way to read whole lines until CTRL+Z is pressed, or something?
is there a way like readLines till CTRL+Z is pressed or something ??
Yes, precisely like this, using the free std::getline function (not the istream method of the same name!):
string line;
while (getline(cin, line)) {
// do something with the line
}
This will read lines (including whitespace, but without ending newline) from the input until either the end of input is reached or cin signals an error.
#include <iostream>
#include <string>
using namespace std;
int main()
string s;
while( getline( cin, s ) ) {
// do something with s
}
}
For my program, I wrote the following bit of code that reads every single character of input until ctrl+x is pressed. Here's the code:
char a;
string b;
while (a != 24)
{
cin.get(a);
b=b+a;
}
cout << b;
For Ctrl+z, enter this:
char a;
string b;
while (a != 26)
{
cin.get(a);
b=b+a;
}
cout << b;
I can't confirm that the ctr+z solution works, as I'm on a UNIX machine, and ctrl+z kills the program. It may or may not work for windows, however; You'd have to see for yourself.
#include <string>
#include <iostream>
int main()
{
std::cout << "enter your name: ";
std::string name;
std::getline(std::cin, name);
return 0;
}
You can use the getline function in c++
#include<iostream>
using namespace std;
int main()
{
char msg[100];
cin.getline(msg,100);
return 0;
}
Related
When you write input in C++, you verify that the input is over by pressing enter, sadly that also changes the line.
But I still want to output something in that particular line.
How can I stay there? Is there a way to change how you confirm the end of the input?
I'm using the Cygwin64 Terminal
You can use getline.
#include <iostream>
int main() {
std::string str;
std::getline(std::cin, str, '.');
std::cout << str;
return 0;
}
Input
abcd.efgh
Output
abcd
Now '.' is an end of input.
getline Reference.
A simple getline() could be used. getline() takes in a delimiter character which can be utilized to "change how you confirm the end of the input". Without that parameter, the default delimiter is \n.
#include <iostream>
using namespace std;
int main()
{
string x;
getline(cin, x, 'm');
cout << x;
}
Input: test1test2mtest3
Output: test1test2
Special characters can also be used, like \t:
#include <iostream>
using namespace std;
int main()
{
string x;
getline(cin, x, '\t');
cout << x;
}
Input:
test1
test2
test3
Output:
test1
test2
A downside that it would still requires users to press Enter to complete the input, as shown above. Because, as #Öö Tiib pointed out:
C++ standard I/O streams are just that ... streams. The C++ is not
addressing from where these come and to where go.
In other words, generally C++ can't control the terminal input/output system, it only knows if something is inputted or if something should be outputted, and feed that to the terminal.
Info : https://en.cppreference.com/w/cpp/string/basic_string/getline
I am a beginner and I'm trying to limit the user to input a single character only, I do aware of using cin.get(char) and it will only read one character from the input, but I don't want the other characters be left in buffer. Here is a sample of my code using EOF, but it doesn't seem to work.
#include <iostream>
#include <sstream>
using namespace std;
string line;
char category;
int main()
{
while (getline (cin, line))
{
if (line.size() == 1)
{
stringstream str(line);
if (str >> category)
{
if (str.eof())
break;
}
}
cout << "Please enter single character only\n";
}
}
I have used this for digit inputs and the eof works fine.
But for the char category the str.eof() seems to be false.
Can someone explain? Thanks in advance.
The eof flag is only set if you read try to read past the end of the stream. If str >> category read past the end of the stream, if (str >> category) would have evaluated false and not entered the loop to test (str.eof()). If there was one character on the line you would have to attempt to read two characters to trigger eof. Reading two characters is far more effort than testing the length of line to see how long it is.
while (getline (cin, line)) got the whole line from the console. If you don't consume it in the stringstream it doesn't matter, that stuff is gone is gone from cin when you loop back around in the while.
In fact, the stringstream isn't doing you any favours. Once you've confirmed the length of the line that was read, you can just use line[0].
#include <iostream>
using namespace std;
int main()
{
string line; // no point to these being global.
char category;
while (getline(cin, line))
{
if (line.size() == 1)
{
//do stuff with line[0];
}
else // need to put the fail case in an else or it runs every time.
// Not very helpful, an error message that prints when the error
// didn't happen.
{
cout << "Please enter single character only\n";
}
}
}
So, I have a file that contains a pattern of a string then an int alternating line by line.
Something like this:
John McClane
30
James Bond
150
Indiana Jones
50
In this example, I would set John McClane to a string variable and then 30 to an integer variable. My issue is dealing with two types. I want to use getline(), but that only works with strings.
Is there an efficient or "right" way of doing this?
There are a number of approaches you could try.
Get string input, and convert to an integer if valid
Convert every second string to an integer
Try to read an integer when you expect one (just using cin >> in;). If you want a robust program, you can check validity with cin.good()
I don't know if there is a "right" way of doing this per say, but it's not a very taxing operation, so whatever you choose should be fine.
You could make a variable like this
string ibuf;
Then convert it to an integer doing this
getline(cin, ibuf);
(Whatever your int variable is) = strtol(ibuf.c_str(), NULL, 10);
One thing about C++ is that there are a large number of ways to accomplish any one task. One way to get integers from strings is to use a stringstream. There is a tutorial on stringstreams here
As for your problem with reading the alternating file, consider the following pseudocode:
boolean isInt = false;
while(fileIsNotOver) {
//getline
if(isInt) {
//use stringstream to get int here
} else {
//do whatever with the name here
}
isInt = !isInt;
}
I don't know if this fully works as i didn't tested it however it just compiles fine and answer should be something like this i think.
#include <iostream>
#include <fstream>
#include <string>
#include <cstdlib>
using namespace std;
int main()
{
int counter = 0;
int number;
string test_string;
ifstream myfile ("example.txt");
if (myfile.is_open())
{
while ( getline (myfile,test_string) )
{
cout << test_string << '\n';
++counter;
if(counter % 2 == 0 ){
number = atoi(test_string.c_str());
cout << number << '\n';
}else{
cout << test_string << '\n';
}
}
myfile.close();
}
else cout << "Unable to open file";
return 0;
}
You can try like this to read a string then an int alternating line by line.
#include<iostream>
#include<string>
#include<cstdio>
using namespace std;
int main()
{
string name;
int number;
freopen("input.txt", "r", stdin);
while (getline(cin, name))
{
cin >> number;
/*
process the input here
...
...
*/
getline(cin, name); // just to read the new line and/or spaces after the integer
//getchar(); //you can use getchar() instead of getline(cin, name) if there is no spaces after the integer
}
return 0;
}
Thanks !!!
I'm writing a function that reads line by line from cin and returns when it sees ; character.
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <string.h>
using namespace std;
int read_cmd(char *cmd)
{
cout << "Please enter a string: \n";
cmd[0]='\0';
while(1){
char currentLine[10000];
currentLine[0]='\0';
cin.getline(currentLine,10000);
if (strcmp(currentLine,";")==0){
break;
}
strcat(cmd, "\n");
strcat(cmd, currentLine);
}
return 0;
}
int main(){
char cmd[1000];
while (1){
read_cmd(cmd);
cout<< cmd << endl;
}
}
I then tested it using text fed from another file via pipe.
./read_cmd < test_file
contents of test_file:
line 1
line 2
;
This outputs results just fine, however it gives me a segmentation fault at the end. Is there a way for cin to check if it's coming across an EOF and terminates?
To detect the EOF you should use something like:
while (cin.good() && !cin.eof())
{
// Read the file
}
See the documentation for cin, in particular the good() (for error checking) and eof() member functions.
In particular this example might be helpful.
I would highly suggest the use of the string object for something like this, that way you're not wasting space, as well as ensuring that you have enouch space. You can also do it without a loop.
string currentLine;
getline(cin, currentLine, ';');
Now, if you need to get just the last line with has the semi-colon, a loop is necessary, but still you can do it at little more easily.
string currentLine;
while(getline(cin, currentLine)){
if(currentLine.find(";") != string::npos){
break;
}
}
Use strings to pass things around as well. There's always the .clear() method as well that any string has for easy emptying.
string getline
string Object
I'm trying to collect user's input in a string variable that accepts whitespaces for a specified amount of time.
Since the usual cin >> str doesn't accept whitespaces, so I'd go with std::getline from <string>
Here is my code:
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
using namespace std;
int main()
{
int n;
cin >> n;
for(int i = 0; i < n; i++)
{
string local;
getline(cin, local); // This simply does not work. Just skipped without a reason.
//............................
}
//............................
return 0;
}
Any idea?
You can see why this is failing if you output what you stored in local (which is a poor variable name, by the way :P):
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
using namespace std;
int main()
{
int n;
cin >> n;
for(int i = 0; i < n; i++)
{
string local;
getline(cin, local);
std::cout << "> " << local << std::endl;
}
//............................
return 0;
}
You will see it prints a newline after > immediately after inputting your number. It then moves on to inputting the rest.
This is because getline is giving you the empty line left over from inputting your number. (It reads the number, but apparently doesn't remove the \n, so you're left with a blank line.) You need to get rid of any remaining whitespace first:
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
using namespace std;
int main()
{
int n;
cin >> n;
cin >> ws; // stream out any whitespace
for(int i = 0; i < n; i++)
{
string local;
getline(cin, local);
std::cout << "> " << local << std::endl;
}
//............................
return 0;
}
This the works as expected.
Off topic, perhaps it was only for the snippet at hand, but code tends to be more readable if you don't have using namespace std;. It defeats the purpose of namespaces. I suspect it was only for posting here, though.
Declare a character to get in the carriage return after you have typed in the number.char ws;int n;cin>>n;ws=cin.get();
This will solve the problem.
Using cin>>ws instead of ws=cin.get(),will make first character of your string to be in variable ws,instead of just clearing '\n'.
It's quite simple.
U jst need to put a cin.get() at the end of the loop.
Are you hitting enter? If not get line will return nothing, as it is waiting for end of line...
My guess is that you're not reading n correctly, so it's converting as zero. Since 0 is not less that 0, the loop never executes.
I'd add a bit of instrumentation:
int n;
cin >> n;
std::cerr << "n was read as: " << n << "\n"; // <- added instrumentation
for // ...
why this happens :
This happens because you have mixed cin and cin.getline.
when you enter a value using cin, cin not only captures the value, it also captures the newline. So when we enter 2, cin actually gets the string “2\n”. It then extracts the 2 to variable, leaving the newline stuck in the input stream. Then, when getline() goes to read the input, it sees “\n” is already in the stream, and figures we must have entered an empty string! Definitely not what was intended.
old solution :
A good rule of thumb is that after reading a value with cin, remove the newline from the stream. This can be done using the following :
std::cin.ignore(32767, '\n'); // ignore up to 32767 characters until a \n is removed
A better solution :
use this whenever you use std::getline() to read strings
std::getline(std::cin >> std::ws, input); // ignore any leading whitespace characters
std::ws is a input manipulator which tell std::getline() to ignore any leading whitespace characters
source : learncpp website
goto section (Use std::getline() to input text)
hope this is helpful
Is n properly initialized from input?
You don't appear to be doing anything with getline. Is this what you want?
getline returns an istream reference. Does the fact that you're dropping it on the ground matter?
On which compiler did you try this? I tried on VC2008 and worked fine. If I compiled the same code on g++ (GCC) 3.4.2. It did not work properly. Below is the versions worked in both compilers. I dont't have the latest g++ compiler in my environment.
int n;
cin >> n;
string local;
getline(cin, local); // don't need this on VC2008. But need it on g++ 3.4.2.
for (int i = 0; i < n; i++)
{
getline(cin, local);
cout << local;
}
The important question is "what are you doing with the string that gives you the idea that the input was skipped?" Or, more accurately, "why do you think the input was skipped?"
If you're stepping through the debugger, did you compile with optimization (which is allowed to reorder instructions)? I don't think this is your problem, but it is a possibility.
I think it's more likely that the string is populated but it's not being handled correctly. For instance, if you want to pass the input to old C functions (eg., atoi()), you will need to extract the C style string (local.c_str()).
You can directly use getline function in string using delimiter as follows:
#include <iostream>
using namespace std;
int main()
{
string str;
getline(cin,str,'#');
getline(cin,str,'#');
}
you can input str as many times as you want but one condition applies here is you need to pass '#'(3rd argument) as delimiter i.e. string will accept input till '#' has been pressed regardless of newline character.
Before getline(cin, local), just add if(i == 0) { cin.ignore(); }. This will remove the last character (\n) from the string, which is causing this problem and its only needed for the first loop. Otherwise, it will remove last character from the string on every iteration. For example,
i = 0 -> string
i = 1 -> strin
i = 2 -> stri
and so on.
just use cin.sync() before the loop.
just add cin.ignore() before getline and it will do the work
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
using namespace std;
int main()
{
int n;
cin >> n;
for(int i = 0; i < n; i++)
{
string local;
cin.ignore();
getline(cin, local);
}
return 0;
}