Link to home
Start Free TrialLog in
Avatar of apolo63
apolo63

asked on

getline in visual c++ 6

im trying to use getline to get a line of input but on execution the getline code is skiped over???

this is the code...

my includes...
#include <iostream>
#include <string>
#include <conio.h>
#include "List.hpp"

using namespace std;

char cTemp[50];
int nLim=50;
cout<<"Please enter a string... \n";
cin.getline(cTemp, nLim, '\n');

I copied the same code into borland and it worked fine.

any help would be cool...

Thanks all,
Apolo.
Avatar of thienpnguyen
thienpnguyen

Avatar of apolo63

ASKER

I got it, there was probably something in the input buffer cause i put the line

cin.get(cKillBuf);

right before that line and it started working...

my question now is...

Is there a command i can use to clear the stdin buffer?
Avatar of apolo63

ASKER

I got it, there was probably something in the input buffer cause i put the line

cin.get(cKillBuf);

right before that line and it started working...

my question now is...

Is there a command i can use to clear the stdin buffer?
im kind of unclear as to what you mean, but i thinkyou might be talking about something like:
cin.flush()
ASKER CERTIFIED SOLUTION
Avatar of cup
cup

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
There is a known bug in the VC version of getline().   You can fix it by changing the code for getline in the STL.

If you open up the string #include file, you'll find this statement:
 
    else if (_Tr::eq(_C, _D))
        {_Chg = true;
        _I.rdbuf()->snextc();    
        break; }
 
If you replace the line:
_I.rdbuf()->snextc();    
 
With:
_I.rdbuf()->sbumpc();  

then recompile and getline() will work fine.
Apolo63,
Cup is correct on his/her comments.  I had the same problem.  What happens is that after the newline, flush, getline see that newline as its input.  If you change '\n' to some other delimiter, like '\'', then getline will accept your input after it see the single quote.  In my code I would of preferred using '\n', so I think I'll go try applying nietod's suggestion.  Using '\n' would be much better.
Apolo63,
 I have tried the following, it works.



#include <iostream.h>  //your problem maybe here, with '.h'
#include <string.h>

void main()
{
     char cTemp[50];
     int nLim=50;
     cout<<"Please enter a string... \n";
     cin.getline(cTemp, nLim, '\n');
     cout<<cTemp;
}
>>  What happens is that after the newline, flush, getline see that newline as its input.
No.  The input and output streams are 100% independant of each other!  think about it.  standard output might be to a line printer and standard input might be a file.  How would informatiojn typed to a peice of paper be read in from a file.

>> #include <iostream.h>  //your problem maybe here, with '.h'
No.  that is your problem, not apolo63's.   apolo63 is using <iostream>, which is the standard STL stream include file.   <iostream.h> is at best a tirvial mistake, but more likely a very dangerious mistake.  There is no standard file with this name.  The contents of that file are unpredictable at best and certainly unportable.

nietod's solution will work if you use std::getline with string instead of char[] i.e.

string cTemp;
getline(cin,str,'\n');

It fixes the problem that you'd get having to input the first line twice.  This is a problem that you sometimes get with MSVC.
AFAIK the fix I posted should fix the global getline AND  the member getline() function.   (The global one is usually a far better one to use, but it should fix both.)  

both version of VC's getline()'s suffer from the same problem.  input streams usually ned to look ahead 1 character.  and buffer this "peeked at" charcter.   VC's problem is that at the end of a line it tries to peek ahead at the next line.  But because of line buffering, it can't obtain the 1st character of the next line until the entire line is entered by the user.  Thus when it tries to peek ahea 1 character, it forces the user to enter an entire line.  This code fixes this problem.
nietod, The member getline doesn't have the same problem as the std::getline because it doesn't use strings.  I used to use the member getline as a fix for the global getline problem.  Your fix works beautifully on std::getline.
>> nietod, The member getline doesn't have the same problem as the
>> std::getline because it doesn't use strings.
the use of STL strings shoudln't matter one way or the other.  The problem is produced when the code tries to peek ahead a character at the end of the line, and that can happen no matter what.  (It could happen when trying to read an int, however it doesn't.)  apolo63 is reporting the problem for istream::getline(), not the global one, so I assume that this problem does occur for both forms of getline().  Its possible that its only for the global getline(), and the member version is experiencing a different one, but I sort of doubt it.

>> I used to use the member getline as a fix for the global getline problem
Did you use soem character other than \n to mark the end of the line?  Even without the fix, the global one worked fine if you terminate the line with some other character.
Without the fix, you will need to input the first line twice for

string cTemp;
getline(cin,str,'\n');

However, with

cin.getline(cTemp, nLim, '\n');

You only need to input once.  Try reversing the fix and you'll see what I mean.


No comment has been added lately, so it's time to clean up this TA. I will
leave a recommendation in the Cleanup topic area that this question is:

Answered: Points to cup: Grade A

Please leave any comments here within the next seven days.

Experts: Silence means you don't care. Grading recommendations are made in light
of the posted grading guidlines (https://www.experts-exchange.com/help.jsp#hi73).

PLEASE DO NOT ACCEPT THIS COMMENT AS AN ANSWER!

-bcl (bcladd)
EE Cleanup Volunteer
cups answer was not correct.  We suggested usign endl because it flushes the output stream.  1st of all, that is not true.  2nd of all, even if it were it wouldn't explain the behavior.  

The problem is a known bug in the libraries shipped with VC 6.
Hate to argue but endl starts a new line and flushes the output stream (http://www.roguewave.com/support/docs/sourcepro/stdlibref/cout.html for starters).

I accept that you pointed out a known bug in the getline implementation but your bug was related to ::getline(istream &, string, char), not istream::getline(char *, int, char) (per http://support.microsoft.com/default.aspx?scid=kb;en-us;240015) and the original poster's code used the latter, not the former.

Since I don't have VC++6.0 installed I cannot test the original poster's code and from his own follow up it is possible that it had nothing to do with the code shown (as shown it would not be possible for anything to be in the input buffer unless there is a previous use of operator>> from cin).

Having explained my answer I will leave it to the moderator who comes through in a week to decide whether this is better deleted, split, or whatever.

-bcl
You're right about endl calling flush.  I just checked the standard.

But the question still remains...so what?  That would have no effect on getline().  

On the other hand, if there is a bug in VC's getline(), as is reported by dincumware, the author of the library at

http://www.dinkumware.com/vc_fixes.html

that would explain the problem.  It would also explain why the code in question worked find borland and developed the problem under VC.
Actually the bug you report has NOTHING to do with the code in question. It is in a different function that has the same name.

It is possible the cup's answer had little to do with the answer, too, now that I reread the original poster's "solution" posting (where he/she solved the problem). Maybe I should just recommend that this question be deleted w/o refund since OP solved it but didn't post the solution.

-bcl