Thread: Quick question: Ifstream and Strings

  1. #1
    Registered User
    Join Date
    Nov 2004
    Location
    Pennsylvania
    Posts
    434

    Quick question: Ifstream and Strings

    Does anybody know how to take the contents of a file and turn them into a string? Ive tried everything i know (im a newb)

  2. #2
    Hello,

    Use Ifstream's read function, maybe?


    - Stack Overflow
    Segmentation Fault: I am an error in which a running program attempts to access memory not allocated to it and core dumps with a segmentation violation error. This is often caused by improper usage of pointers, attempts to access a non-existent or read-only physical memory address, re-use of memory if freed within the same scope, de-referencing a null pointer, or (in C) inadvertently using a non-pointer variable as a pointer.

  3. #3
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    By calling get or getline repeatedly, concatenating the pieces. And being very careful about big files.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  4. #4
    Registered User
    Join Date
    Nov 2004
    Location
    Pennsylvania
    Posts
    434
    CornedBee - What do you mean by the last post? Actually have the program get each word and then like strcat it to a string? I dont think that would work for my program im writing.

    Stack Overflow- Thanks but that READ function doesnt seem to work. I checked out the link too, i tried to implement it but it was a failure

  5. #5
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    Code:
    ifstream if(filename);
    string all, line;
    while(getline(if, line)) {
      all += line;
    }
    I'm not sure if this preserves line breaks, though. Also, it's not very efficient, because it looks at each character. Using the "get" member and a fixed-size character buffer would be more efficient.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  6. #6
    Banned
    Join Date
    Oct 2004
    Posts
    250
    Code:
    #include <iostream>
    #include <fstream>
    using namespace std;
    
    int main()
    {
    	char contents [100];
    	ifstream Open_File ("File.txt", ios::in);
    	Open_File >> contents;
    
    	return 0;
    }
    i think it would be better to use a array like this then you could copy it into a string

  7. #7
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    ifs >> buffer; will discard any leading whitespace and then store consecutive non-whitespace into buffer, this could be, and given the way the world works, will eventually be larger than buffer. You can fix this with a call to either width() or the manipulator setw();
    Code:
        const int bigword_sz = 100;
        char bigword[bigword_sz];
        ...
        ifs >> std::setw(bigword_sz) >> bigword;
     // or
        ifs.width(bigword_sz);
        ifs >> bigword;
    This solves the buffer overflow, but bigword is not the entire file.

    Reading an entire file is almost always a performance killer there are two options to go ahead and do this anyway. One is with std::strings, these expand as needed and can contain any sequence of characters.
    Code:
    class strbased {
        std::string str;
    public:
        strbased(std::istream &is) {
            std::string line;
            while(std::getline(is,line)) {
                if(!is.eof()) line += '\n';
                str += line;
            }
        }
    };
    Note that getline consumes, but does not append the terminating newline. The way to tell if the last line actually ended with a newline is with the test of eof() above. This is also a good example of why the newbe error of looping while(!is.eof()) is a bad idea. Another vairiant of the above is to replace str with a vector of strings and str+=line with lines.push_back(line); Where lines is the vector. In the vector form this is not such a bad way to do this. For the string form the only real reason is if you wanted the ms-dos \r\n => \n conversions.

    You can get about 4-5 times faster if you are willing to mess with the uglyness of your own memory management and use read(), read does not translate.
    Code:
    class readbased {
        char *buff;
        size_t sz;
        readbased & swap(readbased &o) {
            char *tc=buff;buff=o.buff;o.buff=tc;
            size_t ts=sz;sz=o.sz;o.sz=ts;
            return *this;
        }
    public:
        readbased(std::istream &is) : buff(0), sz(0) {
            is.seekg(0,std::ios_base::end);
            sz = is.tellg();
            is.seekg(0);
            buff = new char[sz];
            sz = is.read(buff,sz).gcount();
        }
        readbased(const readbased &rb) : buff(new char[rb.sz]), sz(rb.sz) {
            std::memcpy(buff,rb.buff,sz);
        }
        readbased & operator = (readbased copy) {return swap(copy);}
        ~readbased() {delete [] buff;}
    };
    edit: removed private assignment operator, added the following nagging about loading entire files.

    The biggest problem with loading an entire file into memory is that you are begging to start thrashing. If you run out of phisical memory the os is likely to swap out the least recently used memory. Sooner or later this is going to be the first block of your file. Once that happens your program is going to be competing with the os to read a block as the disk is busy writing a block you read a few seconds ago. Once you are actually done, guess what part of memory you are going to ask for next? a block you have already writen to disk. Reading an entire file often ends up effectively copying a file to the swap file and then reading that entire file back in. Smarter OS's can avoid this to some extent but for any file > phisical memory there is an access pattern that will send any OS, even an optimal one, into a capacity based hell of the blinking disk light.
    Last edited by grib; 12-22-2004 at 12:10 AM.

  8. #8
    Banned
    Join Date
    Oct 2004
    Posts
    250
    here is a way to print out the entire contents of a file
    Code:
    #include <iostream>
    #include <fstream>
    using namespace std;
    
    int main()
    {
    	char contents [100];
    
    	ifstream Open_File ("File.txt", ios::in);
    
    	while(!Open_File.eof())
    	{
    		Open_File >> contents;
    		cout <<contents<<endl;
    	}
    
    	cin.get();
    	return 0;
    }

  9. #9
    Carnivore ('-'v) Hunter2's Avatar
    Join Date
    May 2002
    Posts
    2,879
    >>char contents [100];


    >>while(!Open_File.eof())


    Listen to Stack Overflow, CornedBee and/or grib(?). They actually know what they're talking about

    >>take the contents of a file and turn them into a string
    >>have the program get each word and then like strcat it to a string? I dont think that would work for my program im writing.
    Well, what are you writing? I don't see any problem with what has been suggested.
    Just Google It. √

    (\ /)
    ( . .)
    c(")(") This is bunny. Copy and paste bunny into your signature to help him gain world domination.

  10. #10
    Registered User
    Join Date
    Jan 2003
    Posts
    311
    Quote Originally Posted by Hunter2
    Listen to Stack Overflow, CornedBee and/or grib(?). They actually know what they're talking about
    Listening to me might involve a long, poorly spelled rewrite of readbased to take care of the appalling lack of exception safety. In the process, I'm gonna make you install boost. Your call though.

  11. #11
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    There is no need to go through the hassle of managing your own memory when using read, at least not all of it. You can still use a vector.

    Code:
    ifstream if(filename, ios_base::binary);
    // Simpler, but a little slower. Parentheses must be like I showed them, to avoid a parsing oddity.
    vector<char> data(istreambuf_iterator<char>(if), (istreambuf_iterator<char>()));
    // Faster.
    if.seekg(0, ios_base::end);
    vector<char> data(if.tellg());
    if.seekg(0, ios_base::beg);
    if.read(&data[0], data.size());
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  12. #12
    Registered User
    Join Date
    Sep 2004
    Posts
    719
    [QUOTE=Hunter2]>>char contents [100];


    >>while(!Open_File.eof())



    those red boxes aren't there for no reason
    i seem to have GCC 3.3.4
    But how do i start it?
    I dont have a menu for it or anything.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. question about ifstreams
    By Amyaayaa in forum C++ Programming
    Replies: 6
    Last Post: 05-27-2008, 03:48 PM
  2. ifstream and strings
    By simpleid in forum C++ Programming
    Replies: 2
    Last Post: 11-19-2006, 02:56 AM
  3. Ofstream, Ifstream, Searching files for strings?
    By Zeusbwr in forum C++ Programming
    Replies: 10
    Last Post: 04-04-2005, 03:45 PM
  4. question
    By Gil22 in forum C++ Programming
    Replies: 2
    Last Post: 03-31-2003, 08:36 PM
  5. am I declaring my strings wrong?
    By sunburnbyRA in forum C++ Programming
    Replies: 7
    Last Post: 03-06-2003, 05:42 PM