user847319
user847319

Reputation: 23

c++ getline compile error when called from function

// why does this work?

#include <iostream>
#include <fstream>
#include <string>

using namespace std;

int main() {
  ifstream inputStream("scores.txt");
  string line;
  getline(inputStream, line);
  cout << line;
  return 0;
}

// but this fails with compiler errors.

#include <iostream>
#include <fstream>
#include <string>

using namespace std;

ifstream GetStream() {
  ifstream inputStream("scores.txt");
  return inputStream;
}

int main() {
  ifstream inputStream = GetStream();
  string line;
  getline(inputStream, line);
  cout << line;
  return 0;
}

compile on mac osx 10.6 w/ g++ 4.2.1

georges-iMac:cs106b george$ g++ help.cpp -o help /usr/include/c++/4.2.1/bits/ios_base.h: In copy constructor ‘std::basic_ios >::basic_ios(const std::basic_ios >&)’: /usr/include/c++/4.2.1/bits/ios_base.h:779: error: ‘std::ios_base::ios_base(const std::ios_base&)’ is private /usr/include/c++/4.2.1/iosfwd:55: error: within this context /usr/include/c++/4.2.1/iosfwd: In copy constructor ‘std::basic_ifstream >::basic_ifstream(const std::basic_ifstream >&)’: /usr/include/c++/4.2.1/iosfwd:89: note: synthesized method ‘std::basic_ios >::basic_ios(const std::basic_ios >&)’ first required here /usr/include/c++/4.2.1/streambuf: In copy constructor ‘std::basic_filebuf >::basic_filebuf(const std::basic_filebuf >&)’: /usr/include/c++/4.2.1/streambuf:794: error: ‘std::basic_streambuf<_CharT, _Traits>::basic_streambuf(const std::basic_streambuf<_CharT, _Traits>&) [with _CharT = char, _Traits = std::char_traits]’ is private /usr/include/c++/4.2.1/iosfwd:86: error: within this context /usr/include/c++/4.2.1/iosfwd: In copy constructor ‘std::basic_ifstream >::basic_ifstream(const std::basic_ifstream >&)’: /usr/include/c++/4.2.1/iosfwd:89: note: synthesized method ‘std::basic_filebuf >::basic_filebuf(const std::basic_filebuf >&)’ first required here help.cpp: In function ‘std::ifstream GetStream()’: help.cpp:9: note: synthesized method ‘std::basic_ifstream >::basic_ifstream(const std::basic_ifstream >&)’ first required here

Upvotes: 1

Views: 3260

Answers (3)

Sarfaraz Nawaz
Sarfaraz Nawaz

Reputation: 361442

The problem is with this function:

ifstream GetStream() {
  ifstream inputStream("scores.txt");
  return inputStream;
}

You're returning a stream object by value which is not allowed, because it requires copying of the local object, but you cannot make copy of stream object. Copying of any stream in C++ is disabled by having made the copy constructor private. Any means ANY, whether it is stringstream, istream, ostream, iostream or whatever. Read my post here for the rationale why its disabled:

Now, you may want to return it by reference, but you cannot return it by reference also, because inputStream is a local object.


You may try this:

ifstream* GetStream() {
  return new ifstream("scores.txt");
}

int main() {
  ifstream *inputStream = GetStream();
  if ( inputStream && *inputStream )
  {
    string line;
    getline(*inputStream, line);
    cout << line;
  }
  if ( inputStream )
       delete inputStream; 
  return 0;
}

But I'm wondering why you would do that. Why not encapsulate everything in a class?

Upvotes: 6

Nicola Musatti
Nicola Musatti

Reputation: 18218

Because GetStream() invokes implicitly ifstream's copy constructor, which is invalid because one of ifstreams base classes has a private copy constructor.

Upvotes: 2

Rhexis
Rhexis

Reputation: 2542

i tested it on my windows computer and everything ran fine, no error's whatsoever. not sure whats going on there.

with regards to the first comment(@Nawaz), the line:

ifstream GetStream() {

isnt: ifstream the return type? so must you return that?

Upvotes: 0

Related Questions