Last week on comp.lang.c++.moderated, Nicola Musatti wondered why C++/CLI would use keywords that don't follow the __keyword naming convention for conforming extensions:

  • The standard already provides a way to avoid conflicts when introducing new keywords: prepend a double underscore.

Right, and that's what Managed C++ used, for just that reason: to respect compatibility. Unfortunately, there was a lot of resistance and it is considered a failure.

For one thing, programmers have complained loudly that all the underscores are not only ugly, but a real pain because they're much more common throughout the code than other extensions such as __declspec have been. In particular, __gc gets littered throughout the programmer's code.

At least as importantly, the __keywords littered throughout the code can make the language feel second-class, particularly when people look at equivalent C++ and C# or VB source code side-by-side. This comparative ugliness has been a contributing, if not essential, factor why some programmers have left C++ for other languages.

Consider:

  //-------------------------------------------------------
  // C# code
  //
  class R {
    private int len;
    public property int Length {
      get() { return len; }
      set() { len = value; }
    }
  };

  R r = new R;
  r.Length = 42;

  //-------------------------------------------------------
  // Managed C++ equivalent
  //
  __gc class R {
    int len;
  public:
    __property int get_Length() { return len; }
    __property void set_Length( int i ) { len = i; }
  };

  R __gc * r = new R;
  r.set_Length( 42 );

Oddly, numerous programmers find the former more attractive. Particularly after the 2,000th time they type __gc.

But now we can do better:

  //-------------------------------------------------------
  // C++/CLI equivalent
  //
  ref class R {
    int len;
  public:
    property int Length {
      int get() { return len; }
      void set( int i ) { len = i; }
    }
  };

  R^ r = gcnew R;
  r->Length = 42;

I should note there's actually also a shorter form for this common case, to have the compiler automatically generate the property's getter, setter, and backing store. While I'm at it, I'll also put the R instance on the stack which is also a new feature of the revised syntax:

  //-------------------------------------------------------
  // C++/CLI alternatives
  //
  ref class R {
  public:
    property int Length;
  };

  R r;
  r.Length = 42;

C# is adding something similar as a property shorthand. But C# doesn't have stack-based semantics for reference types and is unlikely to ever have them, though using is a partial automation of the stack-based lifetime control that C++ programmers take for granted. I'll have more to say about using another time.