Section 8.5. String Streams


8.5. String Streams

The iostream library supports in-memory input/output, in which a stream is attached to a string within the program's memory. That string can be written to and read from using the iostream input and output operators. The library defines three kinds of string streams:

  • istringstream, derived from istream, reads from a string.

  • ostringstream, derived from ostream, writes to a string.

  • stringstream, derived from iostream, reads and writes a string.

To use any of these classes, we must include the sstream header.

Like the fstream types, these types are derived from the iostream types, meaning that all the operations on iostreams also apply to the types in sstream. In addition to the operations that the sstream types inherit, these types have a constructor that takes a string. The constructor copies the string argument into the stringstream object. The operations that read and write the stringstream read or write the string in the object. These classes also define a member named str to fetch or set the string value that the stringstream manipulates.

Note that although fstream and sstream share a common base class, they have no other interrelationship. In particular, we cannot use open and close on a stringstream, nor can we use str on an fstream.

Table 8.5. stringstream-Specific Operations

stringstream strm;

Creates an unbound stringstream.

stringstream strm(s);

Creates a stringstream that holds a copy of the string s.

strm.str()

Returns a copy of the string that strm holds.

strm.str(s)

Copies the string s into strm. Returns void.


Using a stringstream

We've seen programs that need to deal with their input a word at a time or a line at a time. The first sort of programs use the string input operator and the second use the getline function. However, some programs need to do both: They have some processing to do on a per-line basis and other work that needs to be done on each word within each line. Using stringstreamslets us do so:

     string line, word;      // will hold a line and word from input, respectively     while (getline(cin, line))   {            // read a line from the input into line        // do per-line processing        istringstream stream(line);            // bind to stream to the line we read        while (stream >> word){          // read a word from line            // do per-word processing        }     } 

Here we use getline to get an entire line from the input. To get the words in each line, we bind an istringstream to the line that we read. We can then use the normal string input operator to read the words from each line.

stringstreams Provide Conversions and/or Formatting

One common use of stringstreams is when we want to obtain automatic formatting across multiple data types. For example, we might have a collection of numeric values but want their string representation or vice versa. The sstream input and output operations automatically convert an arithmetic type into its corresponding string representation or back again:

     int val1 = 512, val2 = 1024;     ostringstream format_message;     // ok: converts values to a string representation     format_message << "val1: " << val1 << "\n"                    << "val2: " << val2 << "\n"; 

Here we create an empty ostringstream object named format_message and insert the indicated text into that object. What's important is that the int values are automatically converted to their printable string equivalents. The contents of format_message are the characters

 val1: 512\nval2: 1024 

We could retrieve the numeric value by using an istringstream to read from the string. Reading an istringstream automatically converts from the character representation of a numeric value to its corresponding arithmetic value:

    // str member obtains the string associated with a stringstream    istringstream input_istring(format_message.str());    string dump; // place to dump the labels from the formatted message    // extracts the stored ascii values, converting back to arithmetic types    input_istring >> dump >> val1 >> dump >> val2;    cout << val1 << " " << val2 << endl;  // prints 512 1024 

Here we use the str member to obtain a copy of the string associated with the ostringstream we previously created. We bind input_istring to that string. When we read input_istring, the values are converted back to their original numeric representations.

To read input_string, we must parse the string into its component parts. We want the numeric values; to get them we must read (and ignore) the labels that are interspersed with the data we want.



Because the input operator reads typed values, it is essential that the types of the objects into which we read be compatible with the types of the values read from the stringstream. In this case, input_istring had four components: The string value val1: followed by 512 followed by the string val2: followed by 1024. As usual, whenweread strings using the input operator, whitespace is ignored. Thus, when we read the string associated with format_message, we can ignore the newlines that are part of that value.

Exercises Section 8.5

Exercise 8.15:

Use the function you wrote for the first exercise in Section 8.2 (p. 291) to print the contents of an istringstream object.

Exercise 8.16:

Write a program to store each line from a file in a vector<string>. Now use an istringstream to read each line from the vector a word at a time.




C++ Primer
C Primer Plus (5th Edition)
ISBN: 0672326965
EAN: 2147483647
Year: 2006
Pages: 223
Authors: Stephen Prata

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net