Главная страница | назад





Article #19434: Why do I have to call the c_str() member function of the String class?

 Question and Answer Database

FAQ4434C.txt - Why do I have to call the c_str() member function of the String class?

Category   :C/C++ Language Issues
Platform   :All-32Bit
Product    :All-CBuilder,   

Question:
Why do I have to call the c_str() member function of the String class?
   Why doesn't the String class simply provide a conversion operator of the
   form:

     operator const char*() const
     {
       return s;
     }

   

Answer:
The String class already provides a way of converting from a const char*
to a String via the conversion constructor:

   String( const char* s );

Adding the operator const char*() above would introduce an ambiguity
during many common operators in which a String and a const char* both
appear in the same expression.  Imagine both a conversion constructor and
an conversion operator for this example:
   String s = "hi";
   if( s == "hi" )... // Convert s to const char* or "hi" to String???

Both conversions from s to const char* and from "hi" to String are
equally easy and will cause an ambiguity error.  The String class
follows a general C++ programming principal of handling this ambiguity
by providing a conversion constructor from some other type to the
String class, but not providing the corresponding conversion operator
for that same type.

Although there may be other solutions to this ambiguity (providing
operator==() for each and every combination of two types that can be
compared, for instance), this solution is easily maintained and doesn't
need to be rewritten when a new type is introduced into the program.

#endif

// To see the ambiguity problem, compile with:
//   bcc32 -DAMBIG
// To see how the String class solves this ambiguity, compile with:
//   bcc32
// Note that this is not a fully functional String class and has many
// missing features, but is presented here in a simplified form for
// clarity.
//
#include 
#include 

class String
{
  private:
  char* s;

  public:
  String( const char*s )
  {
    this->s = newStr( s );
  }

  String( const String& s )
  {
#ifdef AMBIG
    this->s = newStr( s );
#else
    this->s = newStr( s.c_str() );
#endif
  }

 ~String()
  {
    delete[] s;
  }

  char* newStr( const char *s ) const
  {
    char* t = new char[strlen( s ) + 1];
    strncpy( t, s, strlen( s ));
    t[strlen( s )] = 0;
    return t;
  }

#ifdef AMBIG
  operator const char*() const
  {
    return s;
  }
#else
  const char* c_str() const
  {
    return s;
  }
#endif

  bool operator==( const String& s )
  {
    return( strcmp( s.s, this->s ) == 0 );
  }
};

int main()
{
  String s1( "Gavin" );
  String s2 = "Brianna";
  printf( "%s\n", s1 );
  printf( "%s\n", s2 );
  if( s2 == "Brianna" ) puts( " true" );  // Ambiguity???
  else                  puts( "false" );
  return 0;
}

3/29/99 3:50:37 PM
 

Last Modified: 01-SEP-99