Update: Microsoft have released a preview patch to Visual Studio 2012 that adds additional support for C++11 features, most notably for variadic templates. I’m pleased to see that Microsoft responded so quickly to customer outcry (not only mine) that Visual Studio’s C++11 support was far too backward. They moved much more quickly than I thought they would. Maybe we’re looking at a new, faster, leaner, humbler Microsoft. (?)
I’m still waiting for non-static data member initializers, but in other respects I now find Visual Studio 2012 much less of a speed bump to adopting modern C+11 features. So the state of C++ portability is already much less sorry than when I posted this article.
I love C++. I love C++11 to pieces. But poor C++11 support in Visual Studio 2010 and 2012 have made porting modern C++ code a misery.
I recently released an iOS game called House of Shadows that features some sophisticated coding including non-trivial AI and advanced lighting and shadows. It’s written entirely in C++ and uses many C++11 features, including lambdas, std::bind, std::shared_ptr, variadic templates, and non-static data member initializers. It compiles beautifully on iOS, Mac, and Linux using either Clang or GCC.
Yet Visual Studio balks. To see why, make a quick comparison of the charts showing whether Clang or Visual Studio support the various C++11 features. Executive summary: Clang’s chart (like GCC’s) is full of Yes’es; Microsoft’s chart is full of No’s. Because my game uses a wide range of C++11 features, Visual Studio—even Visual Studio 2012—won’t begin to compile it.
Herb Sutter—Microsoft’s chief C++ language guru—recently admitted that Microsoft found implementing variadic templates—a C++11 feature that the open-sourced GCC had already possessed for a couple of years—simply too hard. Makes you wonder about brain drain at Microsoft.
Visual Studio 2010 had promising early support for C++0x, as it was then called. They had lambdas. They had std::shared_ptr. They had function objects and std::bind, albeit in MACRO-mad hacked-together form.
But variadic templates are tremendously helpful for building scriptable C++ objects and introspection systems, and Visual Studio 2012 still lacks them two years later. Non-static data member initializers are syntactic candy, but the guarantee that they provide (data members will be initialized across all constructors) offers a powerful antidote to one of the worst and most common programmer mistakes—namely, forgetting to initialize data.
Put simply, the lack of these and other important features in Visual Studio 2012 means that a C++ programmer wishing to write modern C++11 code must either (1) avoid Windows, (2) avoid using features that make up a significant part of C++11′s value, or (3) use an alternative compiler on Windows.
An alternative compiler is possible. Clang is beautiful and is developing with amazing speed, but its Windows support is still spotty at best.
GCC, on the other hand, works well on Windows now. But it needs help from a build system like MinGW/MSYS. Adopting GCC, therefore, means leaving behind the ease and comfort of Visual Studio and entering the hairy world of UNIX ports, Windows command lines, and makefiles. CMake can help take the edge off managing a project’s build process, but this, too, is a new, non-trivial skill to learn.
Perhaps by 2014 or so, Microsoft will have overcome their intellectual challenges and Visual Studio will have implemented C++11. Until then, creating games or other projects that run across all major platforms will involve mucking about in the wild world of GCC, MinGW, and CMake. If you’re hoping to ride the bus we call the C++ renaissance all the way to cross-platform bliss, just keep an eye out for that sodden pothole.