pBook‎ > ‎BOOST C++‎ > ‎

Boost for Visual C++ Developers

posted Sep 21, 2014, 5:37 PM by Javad Taghia   [ updated Sep 28, 2014, 10:51 AM ]

Boost for Visual C++ Developers

Visual Studio .NET 2003
12 out of 15 rated this helpful Rate this topic
 

Beman Dawes
Founder: Boost.org

May 2004

Summary: Discusses the C++ libraries developed by the Boost community, which add functionality beyond that currently included in the C++ Standard Library. Offers tips to developers for effectively using the Boost libraries, as well as how to contribute to Boost. (11 printed pages)

Contents

Introduction
What Is Boost?
Boost and the C++ Standard Library
Typical Boost Libraries
Smart Pointers
Regular Expressions
Other Interesting Boost Libraries
Using Boost with Visual C++
Tips for Getting the Most Out of Boost Libraries
Contributing to Boost
Conclusion
Related Books
Appendix: The C++ Standard Library Technical Report (TR)

Introduction

It's no secret that powerful libraries pump up C++ programmer productivity by providing ready-made solutions to common programming problems. Use of modern C++ libraries can shorten development cycles and improve the quality of the finished product.

The Boost community developed C++ libraries to add functionality that starts where the current C++ Standard Library leaves off. The Boost libraries are well known for their usefulness, and several have been accepted by the C++ standards committee for eventual ISO standardization.

The much improved C++ language compliance of Microsoft® Visual C++® .NET 2003 now supports full use of the Boost libraries. This article introduces Boost to Visual C++ developers and looks at some of the individual Boost libraries. It discusses Visual C++ IDE set up for Boost, and gives tips for effective use of the Boost libraries. Finally, the article looks at how you can contribute to Boost.

What Is Boost?

Boost is a Web site (www.boost.org) that provides "free peer-reviewed portable C++ source libraries." Boost isn't one library, but a collection of over 50 libraries that work well together. Library interdependencies are limited to cases where a dependency is justified by the value added. Many users start with only one or two Boost libraries, and then expand use over time.

All of Boost, including code, documentation, and everything else on the Web site is free. Free both in the sense of no charge for use of the libraries, and in the sense of no burdensome licenses, even for commercial use. To be accepted by Boost, libraries go through a formal public review. This peer-review process has resulted in very high-quality libraries. The code is portable, to allow use on multiple compilers and operating systems. Regression tests are run daily on more than a dozen compiler and operating system combinations. Source code is distributed for all libraries, so users can inspect, audit, and modify the code to suit local needs.

Boost can also be viewed as an open-source community. Over a hundred volunteer developers work directly on the libraries. Several thousand programmers worldwide participate in mailing lists, newsgroups, formal library reviews, testing, and all the other activities that support the Boost libraries. Commercial support is also available. There are Japanese language and Chinese language Boost mirror sites run by local Boosters in those countries. Universities and corporations, including Microsoft, help out in various ways, such as hosting mailing lists or contributing compilers.

Boost and the C++ Standard Library

The Boost libraries work well with the C++ Standard Library, and about a dozen of them have been accepted for the upcoming Standard Library Technical Report. That means these libraries will eventually be shipped with most C++ compilers. It's too early to say if or when Microsoft might ship the Technical Report libraries, but the Visual C++ team has been very supportive of Boost and the Library Technical Report, and is actively participating in both efforts. The Boost versions of these libraries are available today, and work very nicely with Visual C++ .NET 2003.

Typical Boost Libraries

We'll look at two Boost libraries that are useful in everyday programming: Smart Pointers and Regular Expressions. Both have been accepted for the Library Technical Report.

We'll also take a brief look at the Type Traits and Template Metaprogramming libraries. These infrastructure tools are especially useful  for programmers who develop their own libraries.

Smart Pointers

Memory management in C++ is left up to the programmer. That's great in that it allows critical memory management decisions to be tailored to the application. On the other hand, careless use of heap memory can result in memory leaks and program crashes. Smart pointers are the preferred way in C++ to ensure correct management of dynamic memory allocated by new expressions. Smart pointers are similar to regular pointers, but take care of the details of deleting the object being pointed to when it is no longer needed. The C++ Standard Library already contains std::auto_ptr, a smart pointer with transfer-of-ownership semantics. Boost adds additional smart pointers to handle other common needs, such as shared-ownership semantics.

The Boost shared_ptr class template supplies a shared-ownership smart pointer that can manage dynamically allocated memory in a wide variety of applications, and can be used to intercommunicate with third-party libraries. Unlikestd::auto_ptrshared_ptr works fine with STL containers.

For example, to set up a std::vector of shared_ptr's to a type named Foo, code something like this:

typedef boost::shared_ptr<Foo> FooPtr;
std::vector<FooPtr> foo_vector;

The vector can then be populated like this:

foo_vector.push_back( FooPtr(new Foo(3)) );
foo_vector.push_back( FooPtr(new Foo(2)) );
foo_vector.push_back( FooPtr(new Foo(1)) );

The Shared_ptr Example shown here gives the full code for a sample program:

#include <vector>
#include <iostream>
#include <algorithm>
#include <boost/shared_ptr.hpp>

struct Foo
{ 
  Foo( int _x ) : x(_x) {}
  ~Foo() { std::cout << "Destructing a Foo with x=" << x << "\n"; }
  int x;
  /* ... */
};

typedef boost::shared_ptr<Foo> FooPtr;

struct FooPtrOps
{
  bool operator()( const FooPtr & a, const FooPtr & b )
    { return a->x < b->x; }
  void operator()( const FooPtr & a )
    { std::cout << " " << a->x; }
};

int main()
{
  std::vector<FooPtr> foo_vector;

  foo_vector.push_back( FooPtr(new Foo(3)) );
  foo_vector.push_back( FooPtr(new Foo(2)) );
  foo_vector.push_back( FooPtr(new Foo(1)) );

  std::cout << "Original foo_vector:";
  std::for_each( foo_vector.begin(), foo_vector.end(), FooPtrOps() );
  std::cout << "\n";

  std::sort( foo_vector.begin(), foo_vector.end(), FooPtrOps() );

  std::cout << "Sorted foo_vector:";
  std::for_each( foo_vector.begin(), foo_vector.end(), FooPtrOps() );
  std::cout << "\n";
  return 0;
}

The output will be:

Original foo_vector: 3 2 1
Sorted foo_vector: 1 2 3
Destructing a Foo with x=1
Destructing a Foo with x=2
Destructing a Foo with x=3

The library's documentation includes a page on Smart Pointer Programming Techniques that gives many examples of smart pointer usage, including COM and HANDLE examples in a Microsoft® Windows® environment. For any smart pointer used across DLL boundaries, be sure to set the code generation runtime library option (/MD[d]) consistently so that the modules containing both the new and delete share the same runtime heap.

Regular Expressions

The Boost Regular Expression Library, often called regex++, fills a major hole in the C++ Standard Library. Regular expressions perform generalized string pattern matching, and so are nearly essential for string manipulation chores. Here is a simple example from the library's documentation:

bool validate_card_format(const std::string s)
{
  static const boost::regex e("(\\d{4}[- ]){3}\\d{4}");
  return regex_match(s, e);
}

That regular expression basically says "accept a string if it consists of three sets of four digits followed by a hyphen or a space, and ends with another four digits."

In real applications, regular expressions are often much more complicated. For instance, here is an example for a regular expression that can parse C++ source code and extract class definitions, with class names and specializations identified. This Regular Expression Example comes from several of the library's example programs, which use it to extract class information from C++ program code.

const char* re = 

// possibly leading whitespace: 
"^[[:space:]]*" 

// possible template declaration:
"(template[[:space:]]*<[^;:{]+>[[:space:]]*)?"

// class or struct:
"(class|struct)[[:space:]]*" 

// leading declspec macros etc:
"("
"\\<\\w+\\>"
"("
"[[:blank:]]*\\([^)]*\\)"
")?"
"[[:space:]]*"
")*" 

// the class name
"(\\<\\w*\\>)[[:space:]]*" 

// template specialisation parameters
"(<[^;:{]+>)?[[:space:]]*"

// terminate in { or :
"(\\{|:[^;\\{()]*\\{)";

Since the Microsoft® .NET Framework also supplies a regular expression library, should a Visual C++ programmer use it or the Boost library? That probably depends on the application. An application that may someday be ported to other platforms or may be maintained by programmers unfamiliar with .NET might want to use the Boost library. For pure .NET applications, it may make more sense to stick with the Microsoft regular expressions.

Type Traits

The Boost Type Traits library helps programmers manipulate type information at compile time. It has also been accepted for the Library Technical Report. Uses include supporting a wider variety of types in user-written templates, adding compile-time assertions to improve error detection, and enabling optimizations.

Type traits work by providing templates with a value member that will be true or false. For example:

boost::is_integral<T>::value

If the type T is an integral type according to the language rules, that expression will evaluate to true; otherwise it will evaluate to false. Because it is a compile-time expression, it can be used to alter the course of compilation. That allows use in many generic and metaprogramming contexts. The table below lists all the Boost type traits.

Table 1. Type traits

Primary type <T> categoriesSecondary type <T> categoriesType <T> propertiesRelationships between types <T,U>Transformations to type <T>
is_void
is_integral
is_float
is_pointer
is_reference
is_member_pointer
is_array
is_union
is_class
is_enum
is_function
is_arithmetic
is_fundamental
is_object
is_scalar
is_compound
is_member_function_pointer
is_empty
is_const
is_volatile
is_polymorphic
is_pod
is_abstract
has_trivial_constructor
has_trivial_copy
has_trivial_assign
has_trivial_destructor
is_stateless
has_nothrow_constructor
has_nothrow_copy
has_nothrow_assign
is_same
is_convertible
is_base_and_derived
remove_const
remove_volatile
remove_cv
remove_reference
remove_bounds
remove_pointer
add_reference
add_pointer
add_const
add_volatile
add_cv

The Type Traits Example shown below shows type traits used with the BOOST_STATIC_ASSERT macro to check the validity of a template parameter. Because the check is performed at compile time, there is no run-time cost whatsoever.

#include <boost/static_assert.hpp>
#include <boost/type_traits.hpp>

template< class T >
void foo( T value)
{
  // foo() requires T be integral type
  BOOST_STATIC_ASSERT( boost::is_integral<T>::value );

  // ... actual computations
}

int main()
{
  int i;
  float f;

  foo( i );
  foo( f ); // error! integral type required

  return 0;
}

Metaprogramming

Metaprogramming can be loosely defined as "programs that generate programs." Metaprograms run at compile time, tailoring the code that is actually compiled into the final program. Until recently, metaprogramming was an exotic technique known only to a few researchers, but now C++ metaprogramming is becoming more mainstream with libraries available to handle the details. Boost's metaprogramming libraries provide both preprocessor metaprogramming and template metaprogramming facilities.

The Boost Template Metaprogramming Library (MPL) provides a wealth of operations on types, including control flow, containers, iterators, and algorithms. Here is an example, adapted from the MPL documentation:

template< typename T >
class auto_size_example
   : private mpl::if_< sizeof(T) <= sizeof(double) 
                     , stack_implementation<T>
                     , heap_implementation<T>
                     >::type
{
  // ...
};

When an auto_size_example template is instantiated at compile time, MPL's if_ will determine whether to inherit from stack_implementation or heap_implementation depending on the size of the template parameter T. The net result is an optimization that would be difficult to perform otherwise.

Other Interesting Boost Libraries

Some of the Boost libraries address specific problem domains that not every programmer cares about. For example, the Boost Spirit Library is of interest only to those who need a parser generator, at least at first glance. But Spirit allows extended BNF grammars to be expressed directly in C++, and as such is a considerable intellectual achievement worth studying just for the joy of viewing a world-class design. The Boost Graph Library is another major effort, and a great example of how generic programming concepts can be applied.

In addition to their usefulness, Boost is full of libraries large and small worth studying as design cases. One of the unanticipated benefits of Boost is that it has brought together experienced software developers and innovative academic researchers. That combination has resulted in library designs that are practical yet creative. It isn't uncommon for programmers to read the Boost mailing lists or newsgroups just to watch new Boost library designs evolve.

Using Boost with Visual C++

The first step is to upgrade to Visual C++ .NET 2003. Earlier Visual C++ versions didn't support partial specialization and other template features required by many Boost libraries, making use difficult.

Installing Boost begins by downloading and unzipping the distribution file. A Boost directory tree will be created exactly equivalent to the Web site and containing all files, including sources and documentation.

Many Boost libraries are entirely implemented in their headers, so the only preparation for use beyond downloading and unzipping is to add the Boost root directory to the list of include paths. In the Visual C++ IDE, click Tools |Options... | Projects | VC++ directories. Then in Show Directories for, select Include files and add the path to the Boost root directory.

At that point, you should be ready to use the header-only Boost libraries. You can build and run the Shared_ptr Example shown earlier to verify your set up is complete.

Some of the Boost code does live in object libraries, and so requires a preparatory build. The Boost distribution includes bjam, a powerful and portable make replacement. The scripts (called Jamfiles) to build Boost object libraries are supplied. If Visual C++ is the only compiler you care about, some of the Boost libraries supply make files to build Visual C++ object libraries directly. Boost object library build and install procedures are a weak point at the moment, so expect a few bumps on the road.

Tips for Getting the Most Out of Boost Libraries

Boost libraries develop over time. Sometimes interfaces change, and when a better idea surfaces, an entire library may undergo extensive changes. The older libraries tend to be quite stable, but even so are subject to some change if they become subject to ISO standardization. Rather than take a chance on breaking your existing code, freeze the Boost version your project uses, and only upgrade to a new Boost release when your project is at a point in its lifecycle where a bit of change won't be a problem. If you need a fix for a specific problem, check the Boost CVS to see if a specific fix is available. Because the entire Boost development process is public, you can also ask Boost developers for help with specific problems. There are several mailing lists for support, and these can also be accessed by Web newsgroups. See the Boost Web site for details.

Contributing to Boost

Boost depends on volunteer programmers contributing time and effort; there is no paid staff and the budget is exactly zero. There are a lot of different ways you can contribute to Boost. The most obvious is to contribute a library. But other forms of contribution are equally important.

To be accepted by Boost, libraries go through a formal review process. Anyone can contribute a formal review, and that's a great way to help Boost. Some experienced Boost users help by answering questions from new uses on the Boost-Users mailing list and newsgroup. Some of the larger Boost libraries have their own mailing lists and teams of developers. The best way to get started is to read the main developers mailing list for a while to see how the Boost process works.

Conclusion

The much improved C++ language compliance of Visual C++ .NET 2003 allows full use of the Boost libraries by Visual C++ developers. These community-developed libraries cover a spectrum of needs, ranging from everyday to very specialized. They can be huge productivity boosters, they have interesting designs, and the Boost libraries are absolutely free.

Related Books

Microsoft Visual C++ .Net 2003 Kick Start by Kate Gregory

C++ Templates: The Complete Guide by David Vandevoorde and Nicolai M. Josuttis

The Boost Graph Library: User Guide and Reference by Jeremy G Siek

Appendix: The C++ Standard Library Technical Report (TR)

The C++ Standard Library Technical Report is the ISO C++ Committee's way of gently adding new features to the C++ Standard Library. The additions are "non-normative," meaning that vendors don't have to supply them, although most will. A TR can move through the ISO standardization process more rapidly than a full update to the standard.

Technical Reports often become part of the official standard at a later date. Think of them as 0.9 versions of future releases.

Although details of the Library TR are still being finalized, it looks like most components will be in namespace TR1. When the TR libraries later become full-fledged parts of the Standard Library, they will move to namespace std. This allows the libraries to be changed without breaking existing code. User experience with the TR will determine if such changes are necessary.

A list of libraries that will be in the Library TR is available on the ISO C++ public Web site.

 

About the author

Beman Dawes is a software developer from Virginia in the United States and the founder of boost.org. He is the author of the StreetQuick® geographic atlas library used by digital map publishers to help people get really, really, lost. Beman has been a voting member of the ANSI/ISO C++ Standards Committee since 1992, and chaired the Library Working Group for five years.

Ċ
Javad Taghia,
Sep 28, 2014, 9:55 AM
Comments