Home | History | Annotate | Line # | Download | only in manual
      1 <chapter xmlns="http://docbook.org/ns/docbook" version="5.0"
      2 	 xml:id="std.strings" xreflabel="Strings">
      3 <?dbhtml filename="strings.html"?>
      4 
      5 <info><title>
      6   Strings
      7   <indexterm><primary>Strings</primary></indexterm>
      8 </title>
      9   <keywordset>
     10     <keyword>ISO C++</keyword>
     11     <keyword>library</keyword>
     12   </keywordset>
     13 </info>
     14 
     15 <!-- Sect1 01 : Character Traits -->
     16 
     17 <!-- Sect1 02 : String Classes -->
     18 <section xml:id="std.strings.string" xreflabel="string"><info><title>String Classes</title></info>
     19 
     20 
     21   <section xml:id="strings.string.simple" xreflabel="Simple Transformations"><info><title>Simple Transformations</title></info>
     22 
     23     <para>
     24       Here are Standard, simple, and portable ways to perform common
     25       transformations on a <code>string</code> instance, such as
     26       "convert to all upper case." The word transformations
     27       is especially apt, because the standard template function
     28       <code>transform&lt;&gt;</code> is used.
     29    </para>
     30    <para>
     31      This code will go through some iterations.  Here's a simple
     32      version:
     33    </para>
     34    <programlisting>
     35    #include &lt;string&gt;
     36    #include &lt;algorithm&gt;
     37    #include &lt;cctype&gt;      // old &lt;ctype.h&gt;
     38 
     39    struct ToLower
     40    {
     41      char operator() (char c) const  { return std::tolower(c); }
     42    };
     43 
     44    struct ToUpper
     45    {
     46      char operator() (char c) const  { return std::toupper(c); }
     47    };
     48 
     49    int main()
     50    {
     51      std::string  s ("Some Kind Of Initial Input Goes Here");
     52 
     53      // Change everything into upper case
     54      std::transform (s.begin(), s.end(), s.begin(), ToUpper());
     55 
     56      // Change everything into lower case
     57      std::transform (s.begin(), s.end(), s.begin(), ToLower());
     58 
     59      // Change everything back into upper case, but store the
     60      // result in a different string
     61      std::string  capital_s;
     62      capital_s.resize(s.size());
     63      std::transform (s.begin(), s.end(), capital_s.begin(), ToUpper());
     64    }
     65    </programlisting>
     66    <para>
     67      <emphasis>Note</emphasis> that these calls all
     68       involve the global C locale through the use of the C functions
     69       <code>toupper/tolower</code>.  This is absolutely guaranteed to work --
     70       but <emphasis>only</emphasis> if the string contains <emphasis>only</emphasis> characters
     71       from the basic source character set, and there are <emphasis>only</emphasis>
     72       96 of those.  Which means that not even all English text can be
     73       represented (certain British spellings, proper names, and so forth).
     74       So, if all your input forevermore consists of only those 96
     75       characters (hahahahahaha), then you're done.
     76    </para>
     77    <para><emphasis>Note</emphasis> that the
     78       <code>ToUpper</code> and <code>ToLower</code> function objects
     79       are needed because <code>toupper</code> and <code>tolower</code>
     80       are overloaded names (declared in <code>&lt;cctype&gt;</code> and
     81       <code>&lt;locale&gt;</code>) so the template-arguments for
     82       <code>transform&lt;&gt;</code> cannot be deduced, as explained in
     83       <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/libstdc++/2002-11/msg00180.html">this
     84       message</link>.
     85       <!-- section 14.8.2.4 clause 16 in ISO 14882:1998  -->
     86       At minimum, you can write short wrappers like
     87    </para>
     88    <programlisting>
     89    char toLower (char c)
     90    {
     91       // std::tolower(c) is undefined if c &lt; 0 so cast to unsigned char.
     92       return std::tolower((unsigned char)c);
     93    } </programlisting>
     94    <para>(Thanks to James Kanze for assistance and suggestions on all of this.)
     95    </para>
     96    <para>Another common operation is trimming off excess whitespace.  Much
     97       like transformations, this task is trivial with the use of string's
     98       <code>find</code> family.  These examples are broken into multiple
     99       statements for readability:
    100    </para>
    101    <programlisting>
    102    std::string  str (" \t blah blah blah    \n ");
    103 
    104    // trim leading whitespace
    105    string::size_type  notwhite = str.find_first_not_of(" \t\n");
    106    str.erase(0,notwhite);
    107 
    108    // trim trailing whitespace
    109    notwhite = str.find_last_not_of(" \t\n");
    110    str.erase(notwhite+1); </programlisting>
    111    <para>Obviously, the calls to <code>find</code> could be inserted directly
    112       into the calls to <code>erase</code>, in case your compiler does not
    113       optimize named temporaries out of existence.
    114    </para>
    115 
    116   </section>
    117   <section xml:id="strings.string.case" xreflabel="Case Sensitivity"><info><title>Case Sensitivity</title></info>
    118 
    119     <para>
    120     </para>
    121 
    122    <para>The well-known-and-if-it-isn't-well-known-it-ought-to-be
    123       <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://www.gotw.ca/gotw/">Guru of the Week</link>
    124       discussions held on Usenet covered this topic in January of 1998.
    125       Briefly, the challenge was, <quote>write a 'ci_string' class which
    126       is identical to the standard 'string' class, but is
    127       case-insensitive in the same way as the (common but nonstandard)
    128       C function stricmp()</quote>.
    129    </para>
    130    <programlisting>
    131    ci_string s( "AbCdE" );
    132 
    133    // case insensitive
    134    assert( s == "abcde" );
    135    assert( s == "ABCDE" );
    136 
    137    // still case-preserving, of course
    138    assert( strcmp( s.c_str(), "AbCdE" ) == 0 );
    139    assert( strcmp( s.c_str(), "abcde" ) != 0 ); </programlisting>
    140 
    141    <para>The solution is surprisingly easy.  The original answer was
    142    posted on Usenet, and a revised version appears in Herb Sutter's
    143    book <emphasis>Exceptional C++</emphasis> and on his website as <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://www.gotw.ca/gotw/029.htm">GotW 29</link>.
    144    </para>
    145    <para>See?  Told you it was easy!</para>
    146    <para>
    147      <emphasis>Added June 2000:</emphasis> The May 2000 issue of C++
    148      Report contains a fascinating <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="https://lafstern.org/matt/col2_new.pdf"> article</link> by
    149      Matt Austern (yes, <emphasis>the</emphasis> Matt Austern) on why
    150      case-insensitive comparisons are not as easy as they seem, and
    151      why creating a class is the <emphasis>wrong</emphasis> way to go
    152      about it in production code.  (The GotW answer mentions one of
    153      the principle difficulties; his article mentions more.)
    154    </para>
    155    <para>Basically, this is "easy" only if you ignore some things,
    156       things which may be too important to your program to ignore.  (I chose
    157       to ignore them when originally writing this entry, and am surprised
    158       that nobody ever called me on it...)  The GotW question and answer
    159       remain useful instructional tools, however.
    160    </para>
    161    <para><emphasis>Added September 2000:</emphasis>  James Kanze provided a link to a
    162       <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://www.unicode.org/reports/tr21/tr21-5.html">Unicode
    163       Technical Report discussing case handling</link>, which provides some
    164       very good information.
    165    </para>
    166 
    167   </section>
    168   <section xml:id="strings.string.character_types" xreflabel="Arbitrary Characters"><info><title>Arbitrary Character Types</title></info>
    169 
    170     <para>
    171     </para>
    172 
    173    <para>The <code>std::basic_string</code> is tantalizingly general, in that
    174       it is parameterized on the type of the characters which it holds.
    175       In theory, you could whip up a Unicode character class and instantiate
    176       <code>std::basic_string&lt;my_unicode_char&gt;</code>, or assuming
    177       that integers are wider than characters on your platform, maybe just
    178       declare variables of type <code>std::basic_string&lt;int&gt;</code>.
    179    </para>
    180    <para>That's the theory.  Remember however that basic_string has additional
    181       type parameters, which take default arguments based on the character
    182       type (called <code>CharT</code> here):
    183    </para>
    184    <programlisting>
    185       template &lt;typename CharT,
    186 		typename Traits = char_traits&lt;CharT&gt;,
    187 		typename Alloc = allocator&lt;CharT&gt; &gt;
    188       class basic_string { .... };</programlisting>
    189    <para>Now, <code>allocator&lt;CharT&gt;</code> will probably Do The Right
    190       Thing by default, unless you need to implement your own allocator
    191       for your characters.
    192    </para>
    193    <para>But <code>char_traits</code> takes more work.  The char_traits
    194       template is <emphasis>declared</emphasis> but not <emphasis>defined</emphasis>.
    195       That means there is only
    196    </para>
    197    <programlisting>
    198       template &lt;typename CharT&gt;
    199 	struct char_traits
    200 	{
    201 	    static void foo (type1 x, type2 y);
    202 	    ...
    203 	};</programlisting>
    204    <para>and functions such as char_traits&lt;CharT&gt;::foo() are not
    205       actually defined anywhere for the general case.  The C++ standard
    206       permits this, because writing such a definition to fit all possible
    207       CharT's cannot be done.
    208    </para>
    209    <para>The C++ standard also requires that char_traits be specialized for
    210       instantiations of <code>char</code> and <code>wchar_t</code>, and it
    211       is these template specializations that permit entities like
    212       <code>basic_string&lt;char,char_traits&lt;char&gt;&gt;</code> to work.
    213    </para>
    214    <para>If you want to use character types other than char and wchar_t,
    215       such as <code>unsigned char</code> and <code>int</code>, you will
    216       need suitable specializations for them.  For a time, in earlier
    217       versions of GCC, there was a mostly-correct implementation that
    218       let programmers be lazy but it broke under many situations, so it
    219       was removed.  GCC 3.4 introduced a new implementation that mostly
    220       works and can be specialized even for <code>int</code> and other
    221       built-in types.
    222    </para>
    223    <para>If you want to use your own special character class, then you have
    224       <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/libstdc++/2002-08/msg00163.html">a lot
    225       of work to do</link>, especially if you with to use i18n features
    226       (facets require traits information but don't have a traits argument).
    227    </para>
    228    <para>Another example of how to specialize char_traits was given <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/libstdc++/2002-08/msg00260.html">on the
    229       mailing list</link> and at a later date was put into the file <code>
    230       include/ext/pod_char_traits.h</code>.  We agree
    231       that the way it's used with basic_string (scroll down to main())
    232       doesn't look nice, but that's because <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/libstdc++/2002-08/msg00236.html">the
    233       nice-looking first attempt</link> turned out to <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/libstdc++/2002-08/msg00242.html">not
    234       be conforming C++</link>, due to the rule that CharT must be a POD.
    235       (See how tricky this is?)
    236    </para>
    237 
    238   </section>
    239 
    240   <section xml:id="strings.string.token" xreflabel="Tokenizing"><info><title>Tokenizing</title></info>
    241 
    242     <para>
    243     </para>
    244    <para>The Standard C (and C++) function <code>strtok()</code> leaves a lot to
    245       be desired in terms of user-friendliness.  It's unintuitive, it
    246       destroys the character string on which it operates, and it requires
    247       you to handle all the memory problems.  But it does let the client
    248       code decide what to use to break the string into pieces; it allows
    249       you to choose the "whitespace," so to speak.
    250    </para>
    251    <para>A C++ implementation lets us keep the good things and fix those
    252       annoyances.  The implementation here is more intuitive (you only
    253       call it once, not in a loop with varying argument), it does not
    254       affect the original string at all, and all the memory allocation
    255       is handled for you.
    256    </para>
    257    <para>It's called stringtok, and it's a template function. Sources are
    258    as below, in a less-portable form than it could be, to keep this
    259    example simple (for example, see the comments on what kind of
    260    string it will accept).
    261    </para>
    262 
    263 <programlisting>
    264 #include &lt;string&gt;
    265 template &lt;typename Container&gt;
    266 void
    267 stringtok(Container &amp;container, string const &amp;in,
    268 	  const char * const delimiters = " \t\n")
    269 {
    270     const string::size_type len = in.length();
    271 	  string::size_type i = 0;
    272 
    273     while (i &lt; len)
    274     {
    275 	// Eat leading whitespace
    276 	i = in.find_first_not_of(delimiters, i);
    277 	if (i == string::npos)
    278 	  return;   // Nothing left but white space
    279 
    280 	// Find the end of the token
    281 	string::size_type j = in.find_first_of(delimiters, i);
    282 
    283 	// Push token
    284 	if (j == string::npos)
    285 	{
    286 	  container.push_back(in.substr(i));
    287 	  return;
    288 	}
    289 	else
    290 	  container.push_back(in.substr(i, j-i));
    291 
    292 	// Set up for next loop
    293 	i = j + 1;
    294     }
    295 }
    296 </programlisting>
    297 
    298 
    299    <para>
    300      The author uses a more general (but less readable) form of it for
    301      parsing command strings and the like.  If you compiled and ran this
    302      code using it:
    303    </para>
    304 
    305 
    306    <programlisting>
    307    std::list&lt;string&gt;  ls;
    308    stringtok (ls, " this  \t is\t\n  a test  ");
    309    for (std::list&lt;string&gt;const_iterator i = ls.begin();
    310 	i != ls.end(); ++i)
    311    {
    312        std::cerr &lt;&lt; ':' &lt;&lt; (*i) &lt;&lt; ":\n";
    313    } </programlisting>
    314    <para>You would see this as output:
    315    </para>
    316    <programlisting>
    317    :this:
    318    :is:
    319    :a:
    320    :test: </programlisting>
    321    <para>with all the whitespace removed.  The original <code>s</code> is still
    322       available for use, <code>ls</code> will clean up after itself, and
    323       <code>ls.size()</code> will return how many tokens there were.
    324    </para>
    325    <para>As always, there is a price paid here, in that stringtok is not
    326       as fast as strtok.  The other benefits usually outweigh that, however.
    327    </para>
    328 
    329    <para><emphasis>Added February 2001:</emphasis>  Mark Wilden pointed out that the
    330       standard <code>std::getline()</code> function can be used with standard
    331       <code>istringstreams</code> to perform
    332       tokenizing as well.  Build an istringstream from the input text,
    333       and then use std::getline with varying delimiters (the three-argument
    334       signature) to extract tokens into a string.
    335    </para>
    336 
    337 
    338   </section>
    339   <section xml:id="strings.string.shrink" xreflabel="Shrink to Fit"><info><title>Shrink to Fit</title></info>
    340 
    341     <para>
    342     </para>
    343    <para>From GCC 3.4 calling <code>s.reserve(res)</code> on a
    344       <code>string s</code> with <code>res &lt; s.capacity()</code> will
    345       reduce the string's capacity to <code>std::max(s.size(), res)</code>.
    346    </para>
    347    <para>This behaviour is suggested, but not required by the standard. Prior
    348       to GCC 3.4 the following alternative can be used instead
    349    </para>
    350    <programlisting>
    351       std::string(str.data(), str.size()).swap(str);
    352    </programlisting>
    353    <para>This is similar to the idiom for reducing
    354       a <code>vector</code>'s memory usage
    355       (see <link linkend="faq.size_equals_capacity">this FAQ
    356       entry</link>) but the regular copy constructor cannot be used
    357       because libstdc++'s <code>string</code> is Copy-On-Write in GCC 3.
    358    </para>
    359    <para>From GCC 4.5 in <link linkend="status.iso.2011">C++11</link> mode you
    360       can call <code>s.shrink_to_fit()</code> to achieve the same effect as
    361       <code>s.reserve(s.size())</code>.
    362    </para>
    363 
    364 
    365   </section>
    366 
    367   <section xml:id="strings.string.Cstring" xreflabel="CString (MFC)"><info><title>CString (MFC)</title></info>
    368 
    369     <para>
    370     </para>
    371 
    372    <para>A common lament seen in various newsgroups deals with the Standard
    373       string class as opposed to the Microsoft Foundation Class called
    374       CString.  Often programmers realize that a standard portable
    375       answer is better than a proprietary nonportable one, but in porting
    376       their application from a Win32 platform, they discover that they
    377       are relying on special functions offered by the CString class.
    378    </para>
    379    <para>Things are not as bad as they seem.  In
    380       <link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://gcc.gnu.org/ml/gcc/1999-04n/msg00236.html">this
    381       message</link>, Joe Buck points out a few very important things:
    382    </para>
    383       <itemizedlist>
    384 	 <listitem><para>The Standard <code>string</code> supports all the operations
    385 	     that CString does, with three exceptions.
    386 	 </para></listitem>
    387 	 <listitem><para>Two of those exceptions (whitespace trimming and case
    388 	     conversion) are trivial to implement.  In fact, we do so
    389 	     on this page.
    390 	 </para></listitem>
    391 	 <listitem><para>The third is <code>CString::Format</code>, which allows formatting
    392 	     in the style of <code>sprintf</code>.  This deserves some mention:
    393 	 </para></listitem>
    394       </itemizedlist>
    395    <para>
    396       The old libg++ library had a function called form(), which did much
    397       the same thing.  But for a Standard solution, you should use the
    398       stringstream classes.  These are the bridge between the iostream
    399       hierarchy and the string class, and they operate with regular
    400       streams seamlessly because they inherit from the iostream
    401       hierarchy.  An quick example:
    402    </para>
    403    <programlisting>
    404    #include &lt;iostream&gt;
    405    #include &lt;string&gt;
    406    #include &lt;sstream&gt;
    407 
    408    string f (string&amp; incoming)     // incoming is "foo  N"
    409    {
    410        istringstream   incoming_stream(incoming);
    411        string          the_word;
    412        int             the_number;
    413 
    414        incoming_stream &gt;&gt; the_word        // extract "foo"
    415 		       &gt;&gt; the_number;     // extract N
    416 
    417        ostringstream   output_stream;
    418        output_stream &lt;&lt; "The word was " &lt;&lt; the_word
    419 		     &lt;&lt; " and 3*N was " &lt;&lt; (3*the_number);
    420 
    421        return output_stream.str();
    422    } </programlisting>
    423    <para>A serious problem with CString is a design bug in its memory
    424       allocation.  Specifically, quoting from that same message:
    425    </para>
    426    <programlisting>
    427    CString suffers from a common programming error that results in
    428    poor performance.  Consider the following code:
    429 
    430    CString n_copies_of (const CString&amp; foo, unsigned n)
    431    {
    432 	   CString tmp;
    433 	   for (unsigned i = 0; i &lt; n; i++)
    434 		   tmp += foo;
    435 	   return tmp;
    436    }
    437 
    438    This function is O(n^2), not O(n).  The reason is that each +=
    439    causes a reallocation and copy of the existing string.  Microsoft
    440    applications are full of this kind of thing (quadratic performance
    441    on tasks that can be done in linear time) -- on the other hand,
    442    we should be thankful, as it's created such a big market for high-end
    443    ix86 hardware. :-)
    444 
    445    If you replace CString with string in the above function, the
    446    performance is O(n).
    447    </programlisting>
    448    <para>Joe Buck also pointed out some other things to keep in mind when
    449       comparing CString and the Standard string class:
    450    </para>
    451       <itemizedlist>
    452 	 <listitem><para>CString permits access to its internal representation; coders
    453 	     who exploited that may have problems moving to <code>string</code>.
    454 	 </para></listitem>
    455 	 <listitem><para>Microsoft ships the source to CString (in the files
    456 	     MFC\SRC\Str{core,ex}.cpp), so you could fix the allocation
    457 	     bug and rebuild your MFC libraries.
    458 	     <emphasis><emphasis>Note:</emphasis> It looks like the CString shipped
    459 	     with VC++6.0 has fixed this, although it may in fact have been
    460 	     one of the VC++ SPs that did it.</emphasis>
    461 	 </para></listitem>
    462 	 <listitem><para><code>string</code> operations like this have O(n) complexity
    463 	     <emphasis>if the implementors do it correctly</emphasis>.  The libstdc++
    464 	     implementors did it correctly.  Other vendors might not.
    465 	 </para></listitem>
    466 	 <listitem><para>While parts of the SGI STL are used in libstdc++, their
    467 	     string class is not.  The SGI <code>string</code> is essentially
    468 	     <code>vector&lt;char&gt;</code> and does not do any reference
    469 	     counting like libstdc++'s does.  (It is O(n), though.)
    470 	     So if you're thinking about SGI's string or rope classes,
    471 	     you're now looking at four possibilities:  CString, the
    472 	     libstdc++ string, the SGI string, and the SGI rope, and this
    473 	     is all before any allocator or traits customizations!  (More
    474 	     choices than you can shake a stick at -- want fries with that?)
    475 	 </para></listitem>
    476       </itemizedlist>
    477 
    478   </section>
    479 </section>
    480 
    481 <!-- Sect1 03 : Interacting with C -->
    482 
    483 </chapter>
    484