Managed C++ String Equality (Reference Objects Equality)

March 22, 2007

Here’s a bug that recently crept into my project. A teammate made a simple comparison between strings like this:

String* a = "abc"; 
String* b = "abc"; 
if ( a == b ) { 
     Console::WriteLine ( "success" ); 
} else { 
     Console::WriteLine ( "failed" ); 

Now, in managed C++, every Managed Reference Object have to be declared as __gc* ( garbage collected pointers ). Because of this, every object references are pointers. Thus comparing string as the above will compare reference and not the string itself. People who have not enough understanding on this object will usually treats __gc * objects as if its a real Object. They are not! Furthermore, comparing the above code like this:

*a == *b

also will not be successful. Unfortunately, managed c++ strings doesnt have overloaded operator== that accepts String object as it’s argument. One may wonder, if operator== have overloads for String*, why does it doesn’t kicked in the original code? The answer is, Microsoft could have make its compiler to recognize that the object in question is a managed object and produce code that automatically called the string overloaded operator== operator. However, if they did that, then the compiler won’t be in conformance to standard C/C++. They have no choice but to conform to the standard that says that it should compare the pointers. (Maybe that’s why they invented the C++/CLI).

As a summary, do not compare __gc* objects with operator==, rather use the object ->Equals () method. This goes not only for strings, but to all Managed Reference Objects.


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: