variousauthors20002006Adobe Systems Inc, David Abrahams,
Steve Cleary, Beman Dawes, Aleksey Gurtovoy, Howard Hinnant, Jesse Jones, Mat
Marcus, Itay Maman, John Maddock, Alexander Nasonov, Thorsten Ottosen, Robert
Ramey and Jeremy Siek
Distributed under the Boost Software License, Version 1.0. (See accompanying
file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
Boost.TypeTraits
A printer-friendly PDF
version of this manual is also available.
type-traitsIntroductionIntroductiontype-traitstype-traitsIntroductionIntroductiontype-traitstype-traitsIntroductionIntroductiontype-traits Introduction
The Boost type-traits library contains a set of very specific traits classes,
each of which encapsulate a single trait from the C++ type system; for example,
is a type a pointer or a reference type? Or does a type have a trivial constructor,
or a const-qualifier?
The type-traits classes share a unified design: each class inherits from a
the type true_type
if the type has the specified property and inherits from false_type
otherwise.
The type-traits library also contains a set of classes that perform a specific
transformation on a type; for example, they can remove a top-level const or
volatile qualifier from a type. Each class that performs a transformation defines
a single typedef-member type
that is the result of the transformation.
type-traitsBackground and TutorialBackground and Tutorialtype-traitstype-traitsBackground and TutorialBackground and Tutorialtype-traitsremove_extentBackground and TutorialBackground and Tutorialremove_extentis_pointerBackground and TutorialBackground and Tutorialis_pointeris_voidBackground and TutorialBackground and Tutorialis_voidtype-traitsBackground and TutorialBackground and Tutorialtype-traitstype-traitsBackground and TutorialBackground and Tutorialtype-traitstype-traitsBackground and TutorialBackground and Tutorialtype-traits Background and Tutorial
The following is an updated version of the article "C++ Type traits"
by John Maddock and Steve Cleary that appeared in the October 2000 issue of
Dr Dobb's Journal.
Generic programming (writing code which works with any data type meeting a
set of requirements) has become the method of choice for providing reusable
code. However, there are times in generic programming when "generic"
just isn't good enough - sometimes the differences between types are too large
for an efficient generic implementation. This is when the traits technique
becomes important - by encapsulating those properties that need to be considered
on a type by type basis inside a traits class, we can minimize the amount of
code that has to differ from one type to another, and maximize the amount of
generic code.
Foo1
Consider an example: when working with character strings, one common operation
is to determine the length of a null terminated string. Clearly it's possible
to write generic code that can do this, but it turns out that there are much
more efficient methods available: for example, the C library functions strlen and wcslen
are usually written in assembler, and with suitable hardware support can be
considerably faster than a generic version written in C++. The authors of the
C++ standard library realized this, and abstracted the properties of char and wchar_t
into the class char_traits.
Generic code that works with character strings can simply use char_traits<>::length to determine the length of a null
terminated string, safe in the knowledge that specializations of char_traits will use the most appropriate
method available to them.
Type Traits
Class char_traits is a classic
example of a collection of type specific properties wrapped up in a single
class - what Nathan Myers termed a baggage class[1]. In the Boost type-traits library,
we[2] have written a set of very
specific traits classes, each of which encapsulate a single trait from the
C++ type system; for example, is a type a pointer or a reference type? Or does
a type have a trivial constructor, or a const-qualifier? The type-traits classes
share a unified design: each class inherits from a the type true_type
if the type has the specified property and inherits from false_type
otherwise. As we will show, these classes can be used in generic programming
to determine the properties of a given type and introduce optimizations that
are appropriate for that case.
The type-traits library also contains a set of classes that perform a specific
transformation on a type; for example, they can remove a top-level const or
volatile qualifier from a type. Each class that performs a transformation defines
a single typedef-member type
that is the result of the transformation. All of the type-traits classes are
defined inside namespace boost;
for brevity, namespace-qualification is omitted in most of the code samples
given.
Implementation
There are far too many separate classes contained in the type-traits library
to give a full implementation here - see the source code in the Boost library
for the full details - however, most of the implementation is fairly repetitive
anyway, so here we will just give you a flavor for how some of the classes
are implemented. Beginning with possibly the simplest class in the library,
is_void<T> inherits
from true_type
only if T is void.
template<typenameT>struct is_void :public false_type{};template<>struct is_void<void>:public true_type{};
Here we define a primary version of the template class is_void,
and provide a full-specialization when T
is void. While full specialization
of a template class is an important technique, sometimes we need a solution
that is halfway between a fully generic solution, and a full specialization.
This is exactly the situation for which the standards committee defined partial
template-class specialization. As an example, consider the class boost::is_pointer<T>:
here we needed a primary version that handles all the cases where T is not
a pointer, and a partial specialization to handle all the cases where T is
a pointer:
template<typenameT>struct is_pointer :public false_type{};template<typenameT>struct is_pointer<T*>:public true_type{};
The syntax for partial specialization is somewhat arcane and could easily occupy
an article in its own right; like full specialization, in order to write a
partial specialization for a class, you must first declare the primary template.
The partial specialization contains an extra <...> after the class name
that contains the partial specialization parameters; these define the types
that will bind to that partial specialization rather than the default template.
The rules for what can appear in a partial specialization are somewhat convoluted,
but as a rule of thumb if you can legally write two function overloads of the
form:
voidfoo(T);voidfoo(U);
Then you can also write a partial specialization of the form:
template<typenameT>classc{/*details*/};template<typenameT>classc<U>{/*details*/};
This rule is by no means foolproof, but it is reasonably simple to remember
and close enough to the actual rule to be useful for everyday use.
As a more complex example of partial specialization consider the class remove_extent<T>. This
class defines a single typedef-member type
that is the same type as T but with any top-level array bounds removed; this
is an example of a traits class that performs a transformation on a type:
template<typenameT>struct remove_extent
{typedefTtype;};template<typenameT,std::size_tN>struct remove_extent<T[N]>{typedefTtype;};
The aim of remove_extent
is this: imagine a generic algorithm that is passed an array type as a template
parameter, remove_extent
provides a means of determining the underlying type of the array. For example
remove_extent<int[4][5]>::type would evaluate to the type int[5]. This example also shows that the number of
template parameters in a partial specialization does not have to match the
number in the default template. However, the number of parameters that appear
after the class name do have to match the number and type of the parameters
in the default template.
Optimized copy
As an example of how the type traits classes can be used, consider the standard
library algorithm copy:
template<typenameIter1,typenameIter2>Iter2copy(Iter1first,Iter1last,Iter2out);
Obviously, there's no problem writing a generic version of copy that works
for all iterator types Iter1
and Iter2; however, there are
some circumstances when the copy operation can best be performed by a call
to memcpy. In order to implement
copy in terms of memcpy all
of the following conditions need to be met:
Both of the iterator types Iter1
and Iter2 must be pointers.
Both Iter1 and Iter2 must point to the same type - excluding
const and volatile-qualifiers.
The type pointed to by Iter1
must have a trivial assignment operator.
By trivial assignment operator we mean that the type is either a scalar type[3] or:
The type has no user defined assignment operator.
The type does not have any data members that are references.
All base classes, and all data member objects must have trivial assignment
operators.
If all these conditions are met then a type can be copied using memcpy rather than using a compiler generated
assignment operator. The type-traits library provides a class has_trivial_assign,
such that has_trivial_assign<T>::value is true only if T has a trivial assignment
operator. This class "just works" for scalar types, but has to be
explicitly specialised for class/struct types that also happen to have a trivial
assignment operator. In other words if has_trivial_assign
gives the wrong answer, it will give the "safe" wrong answer - that
trivial assignment is not allowable.
The code for an optimized version of copy that uses memcpy
where appropriate is given in the
examples. The code begins by defining a template function do_copy that performs a "slow but safe"
copy. The last parameter passed to this function may be either a true_type
or a false_type.
Following that there is an overload of docopy that
uses `memcpy`: this time the iterators are required to actually be pointers
to the same type, and the final parameter must be a `_true_type.Finally,theversionofcopycallsdocopy`, passing `_has_trivial_assign<value_type>()`
as the final parameter: this will dispatch to the optimized version where appropriate,
otherwise it will call the "slow but safe version".
Was it worth it?
It has often been repeated in these columns that "premature optimization
is the root of all evil" [4].
So the question must be asked: was our optimization premature? To put this
in perspective the timings for our version of copy compared a conventional
generic copy[5] are shown in table
1.
Clearly the optimization makes a difference in this case; but, to be fair,
the timings are loaded to exclude cache miss effects - without this accurate
comparison between algorithms becomes difficult. However, perhaps we can add
a couple of caveats to the premature optimization rule:
If you use the right algorithm for the job in the first place then optimization
will not be required; in some cases, memcpy is the right algorithm.
If a component is going to be reused in many places by many people then optimizations
may well be worthwhile where they would not be so for a single case - in
other words, the likelihood that the optimization will be absolutely necessary
somewhere, sometime is that much higher. Just as importantly the perceived
value of the stock implementation will be higher: there is no point standardizing
an algorithm if users reject it on the grounds that there are better, more
heavily optimized versions available.
Time taken to copy 1000 elements using `copy<const
T*, T*>` (times in micro-seconds)
Version
T
Time
"Optimized" copy
char
0.99
Conventional copy
char
8.07
"Optimized" copy
int
2.52
Conventional copy
int
8.02
Pair of References
The optimized copy example shows how type traits may be used to perform optimization
decisions at compile-time. Another important usage of type traits is to allow
code to compile that otherwise would not do so unless excessive partial specialization
is used. This is possible by delegating partial specialization to the type
traits classes. Our example for this form of usage is a pair that can hold
references [6].
First, let us examine the definition of std::pair, omitting
the comparison operators, default constructor, and template copy constructor
for simplicity:
template<typenameT1,typenameT2>structpair{typedefT1first_type;typedefT2second_type;T1first;T2second;pair(constT1&nfirst,constT2&nsecond):first(nfirst),second(nsecond){}};
Now, this "pair" cannot hold references as it currently stands, because
the constructor would require taking a reference to a reference, which is currently
illegal [7]. Let us consider what
the constructor's parameters would have to be in order to allow "pair"
to hold non-reference types, references, and constant references:
Required Constructor Argument Types
Type of T1
Type of parameter to initializing constructor
T
const T &
T &
T &
const T &
const T &
A little familiarity with the type traits classes allows us to construct a
single mapping that allows us to determine the type of parameter from the type
of the contained class. The type traits classes provide a transformation add_reference, which
adds a reference to its type, unless it is already a reference.
Using add_reference to synthesize the correct constructor
type
Type of T1
Type of constT1
Type of add_reference<constT1>::type
T
const T
const T &
T &
T & [8]
T &
const T &
const T &
const T &
This allows us to build a primary template definition for pair
that can contain non-reference types, reference types, and constant reference
types:
template<typenameT1,typenameT2>structpair{typedefT1first_type;typedefT2second_type;T1first;T2second;pair(boost::add_reference<constT1>::typenfirst,boost::add_reference<constT2>::typensecond):first(nfirst),second(nsecond){}};
Add back in the standard comparison operators, default constructor, and template
copy constructor (which are all the same), and you have a std::pair that
can hold reference types!
This same extension could have been done using partial template specialization
of pair, but to specialize
pair in this way would require
three partial specializations, plus the primary template. Type traits allows
us to define a single primary template that adjusts itself auto-magically to
any of these partial specializations, instead of a brute-force partial specialization
approach. Using type traits in this fashion allows programmers to delegate
partial specialization to the type traits classes, resulting in code that is
easier to maintain and easier to understand.
Conclusion
We hope that in this article we have been able to give you some idea of what
type-traits are all about. A more complete listing of the available classes
are in the boost documentation, along with further examples using type traits.
Templates have enabled C++ uses to take the advantage of the code reuse that
generic programming brings; hopefully this article has shown that generic programming
does not have to sink to the lowest common denominator, and that templates
can be optimal as well as generic.
Acknowledgements
The authors would like to thank Beman Dawes and Howard Hinnant for their helpful
comments when preparing this article.
References
Nathan C. Myers, C++ Report, June 1995.
The type traits library is based upon contributions by Steve Cleary, Beman
Dawes, Howard Hinnant and John Maddock: it can be found at www.boost.org.
A scalar type is an arithmetic type (i.e. a built-in integer or floating
point type), an enumeration type, a pointer, a pointer to member, or a const-
or volatile-qualified version of one of these types.
This quote is from Donald Knuth, ACM Computing Surveys, December 1974, pg
268.
The test code is available as part of the boost utility library (see algo_opt_examples.cpp),
the code was compiled with gcc 2.95 with all optimisations turned on, tests
were conducted on a 400MHz Pentium II machine running Microsoft Windows 98.
John Maddock and Howard Hinnant have submitted a "compressed_pair"
library to Boost, which uses a technique similar to the one described here
to hold references. Their pair also uses type traits to determine if any
of the types are empty, and will derive instead of contain to conserve space
-- hence the name "compressed".
This is actually an issue with the C++ Core Language Working Group (issue
#106), submitted by Bjarne Stroustrup. The tentative resolution is to allow
a "reference to a reference to T" to mean the same thing as a "reference
to T", but only in template instantiation, in a method similar to multiple
cv-qualifiers.
For those of you who are wondering why this shouldn't be const-qualified,
remember that references are always implicitly constant (for example, you
can't re-assign a reference). Remember also that "const T &"
is something completely different. For this reason, cv-qualifiers on template
type arguments that are references are ignored.
Type Traits by Category Type Traits
that Describe the Properties of a TypeFoo2Bar2
These traits are all value traits, which is to say the
traits classes all inherit from integral_constant,
and are used to access some numerical property of a type. Often this is a
simple true or false Boolean value, but in a few cases may be some other
integer value (for example when dealing with type alignments, or array bounds:
see alignment_of,
rank
and extent).
Categorizing
a Type
These traits identify what "kind" of type some type T is. These are split into two groups:
primary traits which are all mutually exclusive, and composite traits that
are compositions of one or more primary traits.
For any given type, exactly one primary type trait will inherit from true_type,
and all the others will inherit from false_type,
in other words these traits are mutually exclusive.
This means that is_integral<T>::value
and is_floating_point<T>::value
will only ever be true for built-in types; if you want to check for a user-defined
class type that behaves "as if" it is an integral or floating
point type, then use the std::numeric_limitstemplate instead.
Synopsis:template<classT>struct is_array;template<classT>struct is_class;template<classT>struct is_complex;template<classT>struct is_enum;template<classT>struct is_floating_point;template<classT>struct is_function;template<classT>struct is_integral;template<classT>struct is_member_function_pointer;template<classT>struct is_member_object_pointer;template<classT>struct is_pointer;template<classT>struct is_reference;template<classT>struct is_union;template<classT>struct is_void;
The following traits are made up of the union of one or more type categorizations.
A type may belong to more than one of these categories, in addition to
one of the primary categories.
template<classT>struct is_arithmetic;template<classT>struct is_compound;template<classT>struct is_fundamental;template<classT>struct is_member_pointer;template<classT>struct is_object;template<classT>struct is_scalar;
General Type Properties
The following templates describe the general properties of a type.
Synopsis:template<classT>struct alignment_of;template<classT>struct has_nothrow_assign;template<classT>struct has_nothrow_constructor;template<classT>struct has_nothrow_default_constructor;template<classT>struct has_nothrow_copy;template<classT>struct has_nothrow_copy_constructor;template<classT>struct has_trivial_assign;template<classT>struct has_trivial_constructor;template<classT>struct has_trivial_default_constructor;template<classT>struct has_trivial_copy;template<classT>struct has_trivial_copy_constructor;template<classT>struct has_trivial_destructor;template<classT>struct has_virtual_destructor;template<classT>struct is_abstract;template<classT>struct is_const;template<classT>struct is_empty;template<classT>struct is_stateless;template<classT>struct is_pod;template<classT>struct is_polymorphic;template<classT>struct is_signed;template<classT>struct is_unsigned;template<classT>struct is_volatile;template<classT,std::size_tN=0>struct extent;template<classT>struct rank; Relationships
Between Two Types
These templates determine the whether there is a relationship between two
types:
Synopsis:template<classBase,classDerived>struct is_base_of;template<classFrom,classTo>struct is_convertible;template<classT,classU>struct is_same;BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATIONType Traits that Transform One Type to AnotherType Traits that Transform One Type to AnotherBOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATIONBOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATIONType Traits that Transform One Type to AnotherType Traits that Transform One Type to AnotherBOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION Type Traits that
Transform One Type to Another
The following templates transform one type to another, based upon some well-defined
rule. Each template has a single member called type
that is the result of applying the transformation to the template argument
T.
Synopsis:template<classT>struct add_const;template<classT>struct add_cv;template<classT>struct add_pointer;template<classT>struct add_reference;template<classT>struct add_volatile;template<classT>struct decay;template<classT>struct floating_point_promotion;template<classT>struct integral_promotion;template<classT>struct make_signed;template<classT>struct make_unsigned;template<classT>struct promote;template<classT>struct remove_all_extents;template<classT>struct remove_const;template<classT>struct remove_cv;template<classT>struct remove_extent;template<classT>struct remove_pointer;template<classT>struct remove_reference;template<classT>struct remove_volatile;
Broken
Compiler Workarounds:
For all of these templates support for partial specialization of class templates
is required to correctly implement the transformation. On the other hand,
practice shows that many of the templates from this category are very useful,
and often essential for implementing some generic libraries. Lack of these
templates is often one of the major limiting factors in porting those libraries
to compilers that do not yet support this language feature. As some of these
compilers are going to be around for a while, and at least one of them is
very wide-spread, it was decided that the library should provide workarounds
where possible.
The basic idea behind the workaround is to manually define full specializations
of all type transformation templates for all fundamental types, and all their
1st and 2nd rank cv-[un]qualified derivative pointer types, and to provide
a user-level macro that will define all the explicit specializations needed
for any user-defined type T.
The first part guarantees the successful compilation of something like this:
BOOST_STATIC_ASSERT((is_same<char,remove_reference<char&>::type>::value));BOOST_STATIC_ASSERT((is_same<charconst,remove_reference<charconst&>::type>::value));BOOST_STATIC_ASSERT((is_same<charvolatile,remove_reference<charvolatile&>::type>::value));BOOST_STATIC_ASSERT((is_same<charconstvolatile,remove_reference<charconstvolatile&>::type>::value));BOOST_STATIC_ASSERT((is_same<char*,remove_reference<char*&>::type>::value));BOOST_STATIC_ASSERT((is_same<charconst*,remove_reference<charconst*&>::type>::value));...BOOST_STATIC_ASSERT((is_same<charconstvolatile*constvolatile*constvolatile,remove_reference<charconstvolatile*constvolatile*constvolatile&>::type>::value));
and the second part provides the library's users with a mechanism to make
the above code work not only for char,
int or other built-in type,
but for their own types as well:
namespacemyspace{structMyClass{};}// declare this at global scope:
BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION(myspace::MyClass)// transformations on myspace::MyClass now work:
BOOST_STATIC_ASSERT((is_same<myspace::MyClass,remove_reference<myspace::MyClass&>::type>::value));BOOST_STATIC_ASSERT((is_same<myspace::MyClass,remove_const<myspace::MyClassconst>::type>::value));// etc.
Note that the macro BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION evaluates
to nothing on those compilers that do support
partial specialization.
Synthesizing Types
with Specific Alignments
Some low level memory management routines need to synthesize a POD type with
specific alignment properties. The template type_with_alignment
finds the smallest type with a specified alignment, while template aligned_storage
creates a type with a specific size and alignment.
Synopsistemplate<std::size_tAlign>struct type_with_alignment;template<std::size_tSize,std::size_tAlign>struct aligned_storage; Decomposing Function
Types
The class template function_traits
extracts information from function types (see also is_function).
This traits class allows you to tell how many arguments a function takes,
what those argument types are, and what the return type is.
Synopsistemplate<std::size_tAlign>struct function_traits;is_unionUser Defined SpecializationsUser Defined Specializationsis_unionis_classUser Defined SpecializationsUser Defined Specializationsis_class User Defined Specializations
Occationally the end user may need to provide their own specialization for
one of the type traits - typically where intrinsic compiler support is required
to implement a specific trait fully. These specializations should derive from
boost::true_type
or boost::false_type
as appropriate:
#include<boost/type_traits/is_pod.hpp>#include<boost/type_traits/is_class.hpp>#include<boost/type_traits/is_union.hpp>structmy_pod{};structmy_union{charc;inti;};namespaceboost{template<>struct is_pod<my_pod>:public true_type{};template<>struct is_pod<my_union>:public true_type{};template<>struct is_union<my_union>:public true_type{};template<>struct is_class<my_union>:public false_type{};}BOOST_IS_UNIONSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_UNIONBOOST_IS_POLYMORPHICSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_POLYMORPHICBOOST_IS_PODSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_PODBOOST_IS_ENUMSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_ENUMBOOST_IS_EMPTYSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_EMPTYBOOST_IS_CONVERTIBLESupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_CONVERTIBLEBOOST_IS_CLASSSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_CLASSBOOST_IS_BASE_OFSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_BASE_OFBOOST_IS_ABSTRACTSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_IS_ABSTRACTBOOST_HAS_VIRTUAL_DESTRUCTORSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_VIRTUAL_DESTRUCTORBOOST_HAS_TRIVIAL_DESTRUCTORSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_TRIVIAL_DESTRUCTORBOOST_HAS_TRIVIAL_COPYSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_TRIVIAL_COPYBOOST_HAS_TRIVIAL_CONSTRUCTORSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_TRIVIAL_CONSTRUCTORBOOST_HAS_TRIVIAL_ASSIGNSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_TRIVIAL_ASSIGNBOOST_HAS_NOTHROW_COPYSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_NOTHROW_COPYBOOST_HAS_NOTHROW_CONSTRUCTORSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_NOTHROW_CONSTRUCTORBOOST_HAS_NOTHROW_ASSIGNSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_HAS_NOTHROW_ASSIGNBOOST_ALIGNMENT_OFSupport for Compiler IntrinsicsSupport for Compiler IntrinsicsBOOST_ALIGNMENT_OF Support for Compiler Intrinsics
There are some traits that can not be implemented within the current C++ language:
to make these traits "just work" with user defined types, some kind
of additional help from the compiler is required. Currently (April 2008) Visual
C++ 8 and 9, GNU GCC 4.3 and MWCW 9 provide the necessary intrinsics, and other
compilers will no doubt follow in due course.
The Following traits classes always need compiler support to do the right thing
for all types (but all have safe fallback positions if this support is unavailable):
is_union
is_pod
has_trivial_constructor
has_trivial_copy
has_trivial_assign
has_trivial_destructor
has_nothrow_constructor
has_nothrow_copy
has_nothrow_assign
has_virtual_destructor
The following traits classes can't be portably implemented in the C++ language,
although in practice, the implementations do in fact do the right thing on
all the compilers we know about:
is_empty
is_polymorphic
The following traits classes are dependent on one or more of the above:
is_class
is_stateless
The hooks for compiler-intrinsic support are defined in boost/type_traits/intrinsics.hpp,
adding support for new compilers is simply a matter of defining one of more
of the following macros:
Macros for Compiler Intrinsics
BOOST_IS_UNION(T)
Should evaluate to true if T is a union type
BOOST_IS_POD(T)
Should evaluate to true if T is a POD type
BOOST_IS_EMPTY(T)
Should evaluate to true if T is an empty struct or union
BOOST_HAS_TRIVIAL_CONSTRUCTOR(T)
Should evaluate to true if the default constructor for T is trivial (i.e.
has no effect)
BOOST_HAS_TRIVIAL_COPY(T)
Should evaluate to true if T has a trivial copy constructor (and can
therefore be replaced by a call to memcpy)
BOOST_HAS_TRIVIAL_ASSIGN(T)
Should evaluate to true if T has a trivial assignment operator (and can
therefore be replaced by a call to memcpy)
BOOST_HAS_TRIVIAL_DESTRUCTOR(T)
Should evaluate to true if T has a trivial destructor (i.e. ~T() has
no effect)
BOOST_HAS_NOTHROW_CONSTRUCTOR(T)
Should evaluate to true if Tx;
can not throw
BOOST_HAS_NOTHROW_COPY(T)
Should evaluate to true if T(t) can not throw
BOOST_HAS_NOTHROW_ASSIGN(T)
Should evaluate to true if Tt,u;t=u can not throw
BOOST_HAS_VIRTUAL_DESTRUCTOR(T)
Should evaluate to true T has a virtual destructor
BOOST_IS_ABSTRACT(T)
Should evaluate to true if T is an abstract type
BOOST_IS_BASE_OF(T,U)
Should evaluate to true if T is a base class of U
BOOST_IS_CLASS(T)
Should evaluate to true if T is a class type
BOOST_IS_CONVERTIBLE(T,U)
Should evaluate to true if T is convertible to U
BOOST_IS_ENUM(T)
Should evaluate to true is T is an enum
BOOST_IS_POLYMORPHIC(T)
Should evaluate to true if T is a polymorphic type
BOOST_ALIGNMENT_OF(T)
Should evaluate to the alignment requirements of type T.
MPL Interoperability
All the value based traits in this library conform to MPL's requirements for
an Integral
Constant type: that includes a number of rather intrusive workarounds
for broken compilers.
Purely as an implementation detail, this means that true_type
inherits from boost::mpl::true_,
false_type
inherits from boost::mpl::false_,
and integral_constant<T,v>
inherits from boost::mpl::integral_c<T,v>
(provided T is not bool)
Examplesvalue_typeAn Optimized Version of std::copyOptimized Version of std::copyvalue_type An Optimized Version
of std::copy
Demonstrates a version of std::copy
that uses has_trivial_assign
to determine whether to use memcpy
to optimise the copy operation (see copy_example.cpp):
//
// opt::copy
// same semantics as std::copy
// calls memcpy where appropriate.
//
namespacedetail{template<typenameI1,typenameI2,boolb>I2copy_imp(I1first,I1last,I2out,constboost::integral_constant<bool,b>&){while(first!=last){*out=*first;++out;++first;}returnout;}template<typenameT>T*copy_imp(constT*first,constT*last,T*out,constboost::true_type&){memcpy(out,first,(last-first)*sizeof(T));returnout+(last-first);}}template<typenameI1,typenameI2>inlineI2copy(I1first,I1last,I2out){//
// We can copy with memcpy if T has a trivial assignment operator,
// and if the iterator arguments are actually pointers (this last
// requirement we detect with overload resolution):
//
typedeftypenamestd::iterator_traits<I1>::value_typevalue_type;returndetail::copy_imp(first,last,out,boost::has_trivial_assign<value_type>());} An Optimised Version
of std::fill
Demonstrates a version of std::fill
that uses has_trivial_assign
to determine whether to use memset
to optimise the fill operation (see fill_example.cpp):
//
// fill
// same as std::fill, but uses memset where appropriate
//
namespacedetail{template<typenameI,typenameT,boolb>voiddo_fill(Ifirst,Ilast,constT&val,constboost::integral_constant<bool,b>&){while(first!=last){*first=val;++first;}}template<typenameT>voiddo_fill(T*first,T*last,constT&val,constboost::true_type&){std::memset(first,val,last-first);}}template<classI,classT>inlinevoidfill(Ifirst,Ilast,constT&val){//
// We can do an optimised fill if T has a trivial assignment
// operator and if it's size is one:
//
typedefboost::integral_constant<bool,::boost::has_trivial_assign<T>::value&&(sizeof(T)==1)>truth_type;detail::do_fill(first,last,val,truth_type());} An Example that
Omits Destructor Calls For Types with Trivial Destructors
Demonstrates a simple algorithm that uses __has_trivial_destruct
to determine whether to destructors need to be called (see trivial_destructor_example.cpp):
//
// algorithm destroy_array:
// The reverse of std::unitialized_copy, takes a block of
// initialized memory and calls destructors on all objects therein.
//
namespacedetail{template<classT>voiddo_destroy_array(T*first,T*last,constboost::false_type&){while(first!=last){first->~T();++first;}}template<classT>inlinevoiddo_destroy_array(T*first,T*last,constboost::true_type&){}}// namespace detail
template<classT>inlinevoiddestroy_array(T*p1,T*p2){detail::do_destroy_array(p1,p2,::boost::has_trivial_destructor<T>());} An improved Version
of std::iter_swap
Demonstrates a version of std::iter_swap
that use type traits to determine whether an it's arguments are proxying
iterators or not, if they're not then it just does a std::swap
of it's dereferenced arguments (the same as std::iter_swap
does), however if they are proxying iterators then takes special care over
the swap to ensure that the algorithm works correctly for both proxying iterators,
and even iterators of different types (see iter_swap_example.cpp):
//
// iter_swap:
// tests whether iterator is a proxying iterator or not, and
// uses optimal form accordingly:
//
namespacedetail{template<typenameI>staticvoiddo_swap(Ione,Itwo,constboost::false_type&){typedeftypenamestd::iterator_traits<I>::value_typev_t;v_tv=*one;*one=*two;*two=v;}template<typenameI>staticvoiddo_swap(Ione,Itwo,constboost::true_type&){usingstd::swap;swap(*one,*two);}}template<typenameI1,typenameI2>inlinevoiditer_swap(I1one,I2two){//
// See is both arguments are non-proxying iterators,
// and if both iterator the same type:
//
typedeftypenamestd::iterator_traits<I1>::referencer1_t;typedeftypenamestd::iterator_traits<I2>::referencer2_t;typedefboost::integral_constant<bool,::boost::is_reference<r1_t>::value&&::boost::is_reference<r2_t>::value&&::boost::is_same<r1_t,r2_t>::value>truth_type;detail::do_swap(one,two,truth_type());} Convert Numeric
Types and Enums to double
Demonstrates a conversion of Numeric
Types and enum types to double:
template<classT>inlinedoubleto_double(Tconst&value){typedeftypenameboost::promote<T>::typepromoted;returnboost::numeric::converter<double,promoted>::convert(value);} Alphabetical ReferenceConstrained Index Termadd_constadd_constConstrained Index TermConstrained Index Termadd_constadd_constConstrained Index Termadd_constadd_constConstrained Index Termadd_constadd_constConstrained Index TermConstrained Index Termadd_constadd_constConstrained Index Term add_constonetwotemplate<classT>structadd_const{typedefsee-belowtype;};type: The same type as Tconst for all T.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/add_const.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
add_const<int>::typeintconstadd_const<int&>::typeint&add_const<int*>::typeint*constadd_const<intconst>::typeintconst
add_cvadd_cv add_cvonetwothreetemplate<classT>structadd_cv{typedefsee-belowtype;};type: The same type as Tconstvolatile
for all T.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/add_cv.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
add_cv<int>::typeintconstvolatileadd_cv<int&>::typeint&add_cv<int*>::typeint*constvolatileadd_cv<intconst>::typeintconstvolatile
add_pointeradd_pointer add_pointertemplate<classT>structadd_pointer{typedefsee-belowtype;};type: The same type as remove_reference<T>::type*.
The rationale for this template is that it produces the same type as TYPEOF(&t), where
t is an object of type T.
C++ Standard Reference: 8.3.1.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/add_pointer.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
add_pointer<int>::typeint*add_pointer<intconst&>::typeintconst*add_pointer<int*>::typeint**add_pointer<int*&>::typeint**
add_referenceadd_reference add_referencetemplate<classT>structadd_reference{typedefsee-belowtype;};type: If T
is not a reference type then T&, otherwise T.
C++ Standard Reference: 8.3.2.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/add_reference.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
add_reference<int>::typeint&add_reference<intconst&>::typeintconst&add_reference<int*>::typeint*&add_reference<int*&>::typeint*&
add_volatileadd_volatile add_volatileonetemplate<classT>structadd_volatile{typedefsee-belowtype;};type: The same type as Tvolatile for all T.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/add_volatile.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
add_volatile<int>::typeintvolatileadd_volatile<int&>::typeint&add_volatile<int*>::typeint*volatileadd_volatile<intconst>::typeintconstvolatile
aligned_storagealigned_storage aligned_storagetemplate<std::size_tSize,std::size_tAlign>structaligned_storage{typedefsee-belowtype;};type: a built-in or POD type with size
Size and an alignment that
is a multiple of Align.
Header:#include<boost/type_traits/aligned_storage.hpp>
or #include<boost/type_traits.hpp>integral_constantalignment_ofalignment_ofintegral_constantalignment_ofalignment_of alignment_oftemplate<classT>structalignment_of:public integral_constant<std::size_t,ALIGNOF(T)>{};Inherits: Class template alignmentof inherits from `_integral_constant<std::size_t,
ALIGNOF(T)>,whereALIGNOF(T)` is the alignment of type T.
Note: strictly speaking you should only rely on the value of ALIGNOF(T) being
a multiple of the true alignment of T, although in practice it does compute
the correct value in all the cases we know about.Header:#include<boost/type_traits/alignment_of.hpp>
or #include<boost/type_traits.hpp>Examples:
alignment_of<int>
inherits from integral_constant<std::size_t,ALIGNOF(int)>.
alignment_of<char>::type is the type integral_constant<std::size_t,ALIGNOF(char)>.
alignment_of<double>::value is an integral constant expression
with value ALIGNOF(double).
alignment_of<T>::value_type is the type std::size_t.
decaydecay decaytemplate<classT>structdecay{typedefsee-belowtype;};type: Let U
be the result of remove_reference<T>::type, then if U
is an array type, the result is remove_extent<U>*,
otherwise if U is a function
type then the result is U*, otherwise the result is U.
C++ Standard Reference: 3.9.1.
Header:#include<boost/type_traits/decay.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
decay<int[2][3]>::typeint[2]*decay<int(&)[2]>::typeint*decay<int(&)(double)>::typeint(*)(double)int(*)(doubleint(*)(double)int(double)int(*)(double)
integral_constantextentextentintegral_constantextentextent extenttemplate<classT,std::size_tN=0>structextent:public integral_constant<std::size_t,EXTENT(T,N)>{};Inherits: Class template extent inherits
from integral_constant<std::size_t,EXTENT(T,N)>,
where EXTENT(T,N) is the number of elements in the N'th array
dimention of type T.
If T is not an array type,
or if N>
rank<T>::value, or if the N'th array bound is incomplete,
then EXTENT(T,N) is zero.
Header:#include<boost/type_traits/extent.hpp>
or #include<boost/type_traits.hpp>Examples:
extent<int[1]> inherits from integral_constant<std::size_t,1>.
extent<double[2][3][4],1>::type is the type integral_constant<std::size_t,3>.
extent<int[4]>::value
is an integral constant expression that evaluates to 4.
extent<int[][2]>::value is an integral constant expression
that evaluates to 0.
extent<int[][2],1>::value
is an integral constant expression that evaluates to 2.
extent<int*>::value is an integral constant expression
that evaluates to 0.
extent<T>::value_type is the type std::size_t.
floating_point_promotionfloating_point_promotion
floating_point_promotiontemplate<classT>structfloating_point_promotion{typedefsee-belowtype;};type: If floating point promotion can be
applied to an rvalue of type T,
then applies floating point promotion to T
and keeps cv-qualifiers of T,
otherwise leaves T unchanged.
C++ Standard Reference: 4.6.
Header:#include<boost/type_traits/floating_point_promotion.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
floating_point_promotion<floatconst>::typedoubleconstfloating_point_promotion<float&>::typefloat&floating_point_promotion<short>::typeshort
result_typefunction_traitsfunction_traitsresult_typefunction_traitsfunction_traits function_traitstemplate<classF>structfunction_traits{staticconststd::size_tarity=see-below;typedefsee-belowresult_type;typedefsee-below argN_type;};
The class template function_traits will only compile if:
The compiler supports partial specialization of class templates.
The template argument F
is a function type, note that this is not the same thing as a pointer
to a function.
function_traits is intended to introspect only C++ functions of the form
R (), R( A1 ), R ( A1, ... etc. ) and not function pointers or class member
functions. To convert a function pointer type to a suitable type use remove_pointer.
Function Traits Members
Member
Description
function_traits<F>::arity
An integral constant expression that gives the number of arguments
accepted by the function type F.
function_traits<F>::result_type
The type returned by function type F.
function_traits<F>::argN_type
The Nth argument type of function type F,
where 1<=N<=arity of F.
Examples
Expression
Result
function_traits<void(void)>::arity
An integral constant expression that has the value 0.
function_traits<long(int)>::arity
An integral constant expression that has the value 1.
function_traits<long(int,long,double,void*)>::arity
An integral constant expression that has the value 4.
function_traits<void(void)>::result_type
The type void.
function_traits<long(int)>::result_type
The type long.
function_traits<long(int)>::arg1_type
The type int.
function_traits<long(int,long,double,void*)>::arg4_type
The type void*.
function_traits<long(int,long,double,void*)>::arg5_type
A compiler error: there is no arg5_type
since there are only four arguments.
function_traits<long(*)(void)>::arity
A compiler error: argument type is a function pointer,
and not a function type.
has_nothrow_assignhas_nothrow_assign has_nothrow_assigntemplate<classT>structhas_nothrow_assign:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a non-throwing assignment-operator then inherits from true_type,
otherwise inherits from false_type.
Type T must be a complete
type.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_nothrow_assign
will never report that a class or struct has a non-throwing assignment-operator;
this is always safe, if possibly sub-optimal. Currently (May 2005) only Visual
C++ 8 has the necessary compiler support to ensure that this trait "just
works".
Header:#include<boost/type_traits/has_nothrow_assign.hpp>
or #include<boost/type_traits.hpp>has_nothrow_default_constructorhas_nothrow_constructorhas_nothrow_constructorhas_nothrow_default_constructorhas_nothrow_constructorhas_nothrow_constructor
has_nothrow_constructortemplate<classT>structhas_nothrow_constructor:publictrue_type-or-false_type{};template<classT>structhas_nothrow_default_constructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a non-throwing default-constructor then inherits from true_type,
otherwise inherits from false_type.
Type T must be a complete
type.
These two traits are synonyms for each other.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_nothrow_constructor
will never report that a class or struct has a non-throwing default-constructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only Visual
C++ 8 has the necessary compiler intrinsics
to ensure that this trait "just works".
Header:#include<boost/type_traits/has_nothrow_constructor.hpp>
or #include<boost/type_traits.hpp>has_nothrow_copy_constructorhas_nothrow_copyhas_nothrow_copyhas_nothrow_copy_constructorhas_nothrow_copyhas_nothrow_copy has_nothrow_copytemplate<classT>structhas_nothrow_copy:publictrue_type-or-false_type{};template<classT>structhas_nothrow_copy_constructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a non-throwing copy-constructor then inherits from true_type,
otherwise inherits from false_type.
Type T must be a complete
type.
These two traits are synonyms for each other.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_nothrow_copy
will never report that a class or struct has a non-throwing copy-constructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only Visual
C++ 8 has the necessary compiler intrinsics
to ensure that this trait "just works".
Header:#include<boost/type_traits/has_nothrow_copy.hpp>
or #include<boost/type_traits.hpp> has_nothrow_copy_constructor
See has_nothrow_copy.
has_nothrow_default_constructor
See has_nothrow_constructor.
has_trivial_assignhas_trivial_assign has_trivial_assigntemplate<classT>structhas_trivial_assign:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a trivial assignment-operator then inherits from true_type,
otherwise inherits from false_type.
If a type has a trivial assignment-operator then the operator has the same
effect as copying the bits of one object to the other: calls to the operator
can be safely replaced with a call to memcpy.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_trivial_assign
will never report that a user-defined class or struct has a trivial constructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only MWCW
9 and Visual C++ 8 have the necessary compiler intrinsics
to detect user-defined classes with trivial constructors.
C++ Standard Reference: 12.8p11.
Header:#include<boost/type_traits/has_trivial_assign.hpp>
or #include<boost/type_traits.hpp>Examples:
has_trivial_assign<int>
inherits from true_type.
has_trivial_assign<char*>::type is the type true_type.
has_trivial_assign<int(*)(long)>::value is an integral constant expression
that evaluates to true.
has_trivial_assign<MyClass>::value is an integral constant expression
that evaluates to false.
has_trivial_assign<T>::value_type is the type bool.
has_trivial_default_constructorhas_trivial_constructorhas_trivial_constructorhas_trivial_default_constructor
has_trivial_constructortemplate<classT>structhas_trivial_constructor:publictrue_type-or-false_type{};template<classT>structhas_trivial_default_constructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a trivial default-constructor then inherits from true_type,
otherwise inherits from false_type.
These two traits are synonyms for each other.
If a type has a trivial default-constructor then the constructor have no
effect: calls to the constructor can be safely omitted. Note that using meta-programming
to omit a call to a single trivial-constructor call is of no benefit whatsoever.
However, if loops and/or exception handling code can also be omitted, then
some benefit in terms of code size and speed can be obtained.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_trivial_constructor
will never report that a user-defined class or struct has a trivial constructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only MWCW
9 and Visual C++ 8 have the necessary compiler intrinsics
to detect user-defined classes with trivial constructors.
C++ Standard Reference: 12.1p6.
Header:#include<boost/type_traits/has_trivial_constructor.hpp>
or #include<boost/type_traits.hpp>Examples:
has_trivial_constructor<int> inherits from true_type.
has_trivial_constructor<char*>::type
is the type true_type.
has_trivial_constructor<int(*)(long)>::value
is an integral constant expression that evaluates to true.
has_trivial_constructor<MyClass>::value
is an integral constant expression that evaluates to false.
has_trivial_constructor<T>::value_type
is the type bool.
has_trivial_copy_constructorhas_trivial_copyhas_trivial_copyhas_trivial_copy_constructorhas_trivial_copyhas_trivial_copy has_trivial_copytemplate<classT>structhas_trivial_copy:publictrue_type-or-false_type{};template<classT>structhas_trivial_copy_constructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a trivial copy-constructor then inherits from true_type,
otherwise inherits from false_type.
These two traits are synonyms for each other.
If a type has a trivial copy-constructor then the constructor has the same
effect as copying the bits of one object to the other: calls to the constructor
can be safely replaced with a call to memcpy.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_trivial_copy
will never report that a user-defined class or struct has a trivial constructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only MWCW
9 and Visual C++ 8 have the necessary compiler intrinsics
to detect user-defined classes with trivial constructors.
C++ Standard Reference: 12.8p6.
Header:#include<boost/type_traits/has_trivial_copy.hpp>
or #include<boost/type_traits.hpp>Examples:
has_trivial_copy<int>
inherits from true_type.
has_trivial_copy<char*>::type is the type true_type.
has_trivial_copy<int(*)(long)>::value is an integral constant expression
that evaluates to true.
has_trivial_copy<MyClass>::value is an integral constant expression
that evaluates to false.
has_trivial_copy<T>::value_type is the type bool.
has_trivial_copy_constructor
See has_trivial_copy.
has_trivial_default_constructor
See has_trivial_constructor.
has_trivial_destructorhas_trivial_destructor has_trivial_destructortemplate<classT>structhas_trivial_destructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a trivial destructor then inherits from true_type,
otherwise inherits from false_type.
If a type has a trivial destructor then the destructor has no effect: calls
to the destructor can be safely omitted. Note that using meta-programming
to omit a call to a single trivial-constructor call is of no benefit whatsoever.
However, if loops and/or exception handling code can also be omitted, then
some benefit in terms of code size and speed can be obtained.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, has_trivial_destructor
will never report that a user-defined class or struct has a trivial destructor;
this is always safe, if possibly sub-optimal. Currently (May 2005) only MWCW
9 and Visual C++ 8 have the necessary compiler intrinsics
to detect user-defined classes with trivial constructors.
C++ Standard Reference: 12.4p3.
Header:#include<boost/type_traits/has_trivial_destructor.hpp>
or #include<boost/type_traits.hpp>Examples:
has_trivial_destructor<int> inherits from true_type.
has_trivial_destructor<char*>::type
is the type true_type.
has_trivial_destructor<int(*)(long)>::value
is an integral constant expression that evaluates to true.
has_trivial_destructor<MyClass>::value
is an integral constant expression that evaluates to false.
has_trivial_destructor<T>::value_type
is the type bool.
has_virtual_destructorhas_virtual_destructor has_virtual_destructortemplate<classT>structhas_virtual_destructor:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
type with a virtual destructor then inherits from true_type,
otherwise inherits from false_type.
Compiler Compatibility: This trait is provided
for completeness, since it's part of the Technical Report on C++ Library
Extensions. However, there is currently no way to portably implement this
trait. The default version provided always inherits from false_type,
and has to be explicitly specialized for types with virtual destructors unless
the compiler used has compiler intrinsics
that enable the trait to do the right thing: currently (May 2005) only Visual
C++ 8 and GCC-4.3 have the necessary intrinsics.
C++ Standard Reference: 12.4.
Header:#include<boost/type_traits/has_virtual_destructor.hpp>
or #include<boost/type_traits.hpp>value_typeintegral_constantintegral_constantvalue_typetrue_typeintegral_constantintegral_constanttrue_typeintegral_constantintegral_constantfalse_typeintegral_constantintegral_constantfalse_type integral_constanttemplate<classT,Tval>structintegral_constant{typedefintegral_constant<T,val>type;typedefTvalue_type;staticconstTvalue=val;};typedefintegral_constant<bool,true>true_type;typedefintegral_constant<bool,false>false_type;
Class template integral_constant
is the common base class for all the value-based type traits. The two typedef's
true_type and false_type are provided for convenience:
most of the value traits are Boolean properties and so will inherit from
one of these.
integral_promotionintegral_promotion integral_promotiontemplate<classT>structintegral_promotion{typedefsee-belowtype;};type: If integral promotion can be applied
to an rvalue of type T, then
applies integral promotion to T
and keeps cv-qualifiers of T,
otherwise leaves T unchanged.
C++ Standard Reference: 4.5 except 4.5/3
(integral bit-field).
Header:#include<boost/type_traits/integral_promotion.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
integral_promotion<shortconst>::typeintconstintegral_promotion<short&>::typeshort&integral_promotion<enumstd::float_round_style>::typeint
is_abstractis_abstract is_abstracttemplate<classT>structis_abstract:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
abstract type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 10.3.
Header:#include<boost/type_traits/is_abstract.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: The compiler must
support DR337 (as of April 2005: GCC 3.4, VC++ 7.1 (and later), Intel C++
7 (and later), and Comeau 4.3.2). Otherwise behaves the same as is_polymorphic;
this is the "safe fallback position" for which polymorphic types
are always regarded as potentially abstract. The macro BOOST_NO_IS_ABSTRACT
is used to signify that the implementation is buggy, users should check for
this in their own code if the "safe fallback" is not suitable for
their particular use-case.
Examples:
Given: classabc{virtual~abc()=0;};
is_abstract<abc>
inherits from true_type.
is_abstract<abc>::type is the type true_type.
is_abstract<abcconst>::value
is an integral constant expression that evaluates to true.
is_abstract<T>::value_type is the type bool.
is_arithmeticis_arithmetic is_arithmetictemplate<classT>structis_arithmetic:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
arithmetic type then inherits from true_type,
otherwise inherits from false_type.
Arithmetic types include integral and floating point types (see also is_integral and
is_floating_point).
C++ Standard Reference: 3.9.1p8.
Header:#include<boost/type_traits/is_arithmetic.hpp>
or #include<boost/type_traits.hpp>Examples:
is_arithmetic<int>
inherits from true_type.
is_arithmetic<char>::type is the type true_type.
is_arithmetic<double>::value is an integral constant expression
that evaluates to true.
is_arithmetic<T>::value_type is the type bool.
is_arrayis_array is_arraytemplate<classT>structis_array:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
array type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 8.3.4.
Header:#include<boost/type_traits/is_array.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can give the wrong result with function types.
Examples:
is_array<int[2]> inherits from true_type.
is_array<char[2][3]>::type
is the type true_type.
is_array<double[]>::value is an integral constant expression
that evaluates to true.
is_array<T>::value_type is the type bool.
is_base_ofis_base_of is_base_oftemplate<classBase,classDerived>structis_base_of:publictrue_type-or-false_type{};Inherits: If Base is base class of type
Derived or if both types are the same then inherits from true_type,
otherwise inherits from false_type.
This template will detect non-public base classes, and ambiguous base classes.
Note that is_base_of<X,X> will always inherit from true_type.
This is the case even if X
is not a class type. This is a change in behaviour from Boost-1.33
in order to track the Technical Report on C++ Library Extensions.
Types Base and Derived must not be incomplete types.
C++ Standard Reference: 10.
Header:#include<boost/type_traits/is_base_of.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types. There are some older compilers which
will produce compiler errors if Base
is a private base class of Derived,
or if Base is an ambiguous
base of Derived. These compilers
include Borland C++, older versions of Sun Forte C++, Digital Mars C++, and
older versions of EDG based compilers.
Examples:
Given: classBase{};classDerived:publicBase{};
is_base_of<Base,Derived>
inherits from true_type.
is_base_of<Base,Derived>::type is the type true_type.
is_base_of<Base,Derived>::value is an integral constant expression
that evaluates to true.
is_base_of<Base,Derived>::value is an integral constant expression
that evaluates to true.
is_base_of<Base,Base>::value is an integral constant expression
that evaluates to true: a class is regarded as it's
own base.
is_base_of<T>::value_type is the type bool.
is_classis_class is_classtemplate<classT>structis_class:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
class type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 9.2.
Header:#include<boost/type_traits/is_class.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: Without (some as
yet unspecified) help from the compiler, we cannot distinguish between union
and class types, as a result this type will erroneously inherit from true_type for
union types. See also is_union.
Currently (May 2005) only Visual C++ 8 has the necessary compiler intrinsics
to correctly identify union types, and therefore make is_class function correctly.
Examples:
Given: classMyClass; then:
is_class<MyClass>
inherits from true_type.
is_class<MyClassconst>::type
is the type true_type.
is_class<MyClass>::value is an integral constant expression
that evaluates to true.
is_class<MyClass&>::value is an integral constant expression
that evaluates to false.
is_class<MyClass*>::value is an integral constant expression
that evaluates to false.
is_class<T>::value_type is the type bool.
is_complexis_complex is_complextemplate<classT>structis_complex:publictrue_type-or-false_type{};Inherits: If T
is a complex number type then true (of type std::complex<U>
for some type U), otherwise
false.
C++ Standard Reference: 26.2.
Header:#include<boost/type_traits/is_complex.hpp>
or #include<boost/type_traits.hpp>is_compoundis_compound is_compoundtemplate<classT>structis_compound:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
compound type then inherits from true_type,
otherwise inherits from false_type.
Any type that is not a fundamental type is a compound type (see also is_fundamental).
C++ Standard Reference: 3.9.2.
Header:#include<boost/type_traits/is_compound.hpp>
or #include<boost/type_traits.hpp>Examples:
is_compound<MyClass>
inherits from true_type.
is_compound<MyEnum>::type is the type true_type.
is_compound<int*>::value is an integral constant expression
that evaluates to true.
is_compound<int&>::value is an integral constant expression
that evaluates to true.
is_compound<int>::value is an integral constant expression
that evaluates to false.
is_compound<T>::value_type is the type bool.
is_constis_const is_consttemplate<classT>structis_const:publictrue_type-or-false_type{};Inherits: If T is a (top level) const-qualified
type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.3.
Header:#include<boost/type_traits/is_const.hpp>
or #include<boost/type_traits.hpp>Examples:
is_const<intconst> inherits from true_type.
is_const<intconstvolatile>::type is the type true_type.
is_const<int*const>::value is an integral constant expression
that evaluates to true.
is_const<intconst*>::value
is an integral constant expression that evaluates to false:
the const-qualifier is not at the top level in this case.
is_const<intconst&>::value
is an integral constant expression that evaluates to false:
the const-qualifier is not at the top level in this case.
is_const<int>::value is an integral constant expression
that evaluates to false.
is_const<T>::value_type is the type bool.
is_convertibleis_convertible is_convertibletemplate<classFrom,classTo>structis_convertible:publictrue_type-or-false_type{};Inherits: If an imaginary lvalue of type
From is convertible to type
To then inherits from true_type,
otherwise inherits from false_type.
Type From must not be an incomplete type.
Type To must not be an incomplete, or function type.
No types are considered to be convertible to array types or abstract-class
types.
This template can not detect whether a converting-constructor is public or not: if type To
has a private converting constructor
from type From then instantiating
is_convertible<From,To>
will produce a compiler error. For this reason is_convertible
can not be used to determine whether a type has a public
copy-constructor or not.
This template will also produce compiler errors if the conversion is ambiguous,
for example:
structA{};structB:A{};structC:A{};structD:B,C{};// This produces a compiler error, the conversion is ambiguous:
boolconsty=boost::is_convertible<D*,A*>::value;C++ Standard Reference: 4 and 8.5.
Compiler Compatibility: This template is
currently broken with Borland C++ Builder 5 (and earlier), for constructor-based
conversions, and for the Metrowerks 7 (and earlier) compiler in all cases.
If the compiler does not support is_abstract,
then the template parameter To
must not be an abstract type.
Header:#include<boost/type_traits/is_convertible.hpp>
or #include<boost/type_traits.hpp>Examples:
is_convertible<int,double>
inherits from true_type.
is_convertible<constint,double>::type
is the type true_type.
is_convertible<int*const,int*>::value is an integral constant expression
that evaluates to true.
is_convertible<intconst*,int*>::value
is an integral constant expression that evaluates to false:
the conversion would require a const_cast.
is_convertible<intconst&,long>::value
is an integral constant expression that evaluates to true.
is_convertible<int>::value is an integral constant expression
that evaluates to false.
is_convertible<T>::value_type is the type bool.
is_emptyis_empty is_emptytemplate<classT>structis_empty:publictrue_type-or-false_type{};Inherits: If T is an empty class type then
inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 10p5.
Header:#include<boost/type_traits/is_empty.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: In order to correctly
detect empty classes this trait relies on either:
the compiler implementing zero sized empty base classes, or
the compiler providing intrinsics
to detect empty classes.
Can not be used with incomplete types.
Can not be used with union types, until is_union can be made to work.
If the compiler does not support partial-specialization of class templates,
then this template can not be used with abstract types.
Examples:
Given: structempty_class{};
is_empty<empty_class>
inherits from true_type.
is_empty<empty_classconst>::type
is the type true_type.
is_empty<empty_class>::value is an integral constant expression
that evaluates to true.
is_empty<T>::value_type is the type bool.
is_enumis_enum is_enumtemplate<classT>structis_enum:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
enum type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 7.2.
Header:#include<boost/type_traits/is_enum.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: Requires a correctly
functioning is_convertible
template; this means that is_enum is currently broken under Borland C++ Builder
5, and for the Metrowerks compiler prior to version 8, other compilers should
handle this template just fine.
Examples:
Given: enummy_enum{one,two};
is_enum<my_enum>
inherits from true_type.
is_enum<my_enumconst>::type
is the type true_type.
is_enum<my_enum>::value is an integral constant expression
that evaluates to true.
is_enum<my_enum&>::value is an integral constant expression
that evaluates to false.
is_enum<my_enum*>::value is an integral constant expression
that evaluates to false.
is_enum<T>::value_type is the type bool.
is_floating_pointis_floating_point is_floating_pointtemplate<classT>structis_floating_point:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
floating point type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.1p8.
Header:#include<boost/type_traits/is_floating_point.hpp>
or #include<boost/type_traits.hpp>Examples:
is_floating_point<float>
inherits from true_type.
is_floating_point<double>::type is the type true_type.
is_floating_point<longdouble>::value
is an integral constant expression that evaluates to true.
is_floating_point<T>::value_type is the type bool.
is_functionis_function is_functiontemplate<classT>structis_function:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
function type then inherits from true_type,
otherwise inherits from false_type.
Note that this template does not detect pointers to functions,
or references to functions, these are detected by is_pointer and is_reference respectively:
typedefintf1();// f1 is of function type.
typedefint(f2*)();// f2 is a pointer to a function.
typedefint(f3&)();// f3 is a reference to a function.
C++ Standard Reference: 3.9.2p1 and 8.3.5.
Header:#include<boost/type_traits/is_function.hpp>
or #include<boost/type_traits.hpp>Examples:
is_function<int(void)>
inherits from true_type.
is_function<long(double,int)>::type is the type true_type.
is_function<long(double,int)>::value is an integral constant expression
that evaluates to true.
is_function<long(*)(double,int)>::value is an integral constant expression
that evaluates to false: the argument in this case
is a pointer type, not a function type.
is_function<long(&)(double,int)>::value is an integral constant expression
that evaluates to false: the argument in this case
is a reference to a function, not a function type.
is_function<long(MyClass::*)(double,int)>::value is an integral constant expression
that evaluates to false: the argument in this case
is a pointer to a member function.
is_function<T>::value_type is the type bool.
Don't confuse function-types with pointers to functions:
typedefintf(double);
defines a function type,
ffoo;
declares a prototype for a function of type f,
f*pf=foo;f&fr=foo;
declares a pointer and a reference to the function foo.
If you want to detect whether some type is a pointer-to-function then use:
is_function<remove_pointer<T>::type>::value&& is_pointer<T>::value
or for pointers to member functions you can just use is_member_function_pointer
directly.
is_fundamentalis_fundamental is_fundamentaltemplate<classT>structis_fundamental:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
fundamental type then inherits from true_type,
otherwise inherits from false_type.
Fundamental types include integral, floating point and void types (see also
is_integral,
is_floating_point
and is_void)
C++ Standard Reference: 3.9.1.
Header:#include<boost/type_traits/is_fundamental.hpp>
or #include<boost/type_traits.hpp>Examples:
is_fundamental<int)>
inherits from true_type.
is_fundamental<doubleconst>::type
is the type true_type.
is_fundamental<void>::value is an integral constant expression
that evaluates to true.
is_fundamental<T>::value_type is the type bool.
is_integralis_integral is_integraltemplate<classT>structis_integral:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
integral type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.1p7.
Header:#include<boost/type_traits/is_integral.hpp>
or #include<boost/type_traits.hpp>Examples:
is_integral<int>
inherits from true_type.
is_integral<constchar>::type
is the type true_type.
is_integral<long>::value is an integral constant expression
that evaluates to true.
is_integral<T>::value_type is the type bool.
is_member_function_pointeris_member_function_pointer
is_member_function_pointertemplate<classT>structis_member_function_pointer:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
pointer to a member function then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 8.3.3.
Header:#include<boost/type_traits/is_member_function_pointer.hpp>
or #include<boost/type_traits.hpp>Examples:
is_member_function_pointer<int(MyClass::*)(void)> inherits from true_type.
is_member_function_pointer<int(MyClass::*)(char)>::type
is the type true_type.
is_member_function_pointer<int(MyClass::*)(void)const>::value
is an integral constant expression that evaluates to true.
is_member_function_pointer<int(MyClass::*)>::value
is an integral constant expression that evaluates to false:
the argument in this case is a pointer to a data member and not a member
function, see is_member_object_pointer
and is_member_pointer
is_member_function_pointer<T>::value_type
is the type bool.
is_member_object_pointeris_member_object_pointer
is_member_object_pointertemplate<classT>structis_member_object_pointer:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
pointer to a member object (a data member) then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 8.3.3.
Header:#include<boost/type_traits/is_member_object_pointer.hpp>
or #include<boost/type_traits.hpp>Examples:
is_member_object_pointer<int(MyClass::*)> inherits from true_type.
is_member_object_pointer<double(MyClass::*)>::type
is the type true_type.
is_member_object_pointer<constint(MyClass::*)>::value is an integral constant expression
that evaluates to true.
is_member_object_pointer<int(MyClass::*)(void)>::value
is an integral constant expression that evaluates to false:
the argument in this case is a pointer to a member function and not a
member object, see is_member_function_pointer
and is_member_pointer
is_member_object_pointer<T>::value_type
is the type bool.
is_member_pointeris_member_pointer is_member_pointertemplate<classT>structis_member_pointer:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
pointer to a member (either a function or a data member) then inherits from
true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 8.3.3.
Header:#include<boost/type_traits/is_member_pointer.hpp>
or #include<boost/type_traits.hpp>Examples:
is_member_pointer<int(MyClass::*)>
inherits from true_type.
is_member_pointer<int(MyClass::*)(char)>::type is the type true_type.
is_member_pointer<int(MyClass::*)(void)const>::value is an integral constant expression
that evaluates to true.
is_member_pointer<T>::value_type is the type bool.
is_objectis_object is_objecttemplate<classT>structis_object:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
object type then inherits from true_type,
otherwise inherits from false_type.
All types are object types except references, void, and function types.
C++ Standard Reference: 3.9p9.
Header:#include<boost/type_traits/is_object.hpp>
or #include<boost/type_traits.hpp>Examples:
is_object<int>
inherits from true_type.
is_object<int*>::type is the type true_type.
is_object<int(*)(void)>::value is an integral constant expression
that evaluates to true.
is_object<int(MyClass::*)(void)const>::value is an integral constant expression
that evaluates to true.
is_object<int&>::value is an integral constant expression
that evaluates to false: reference types are not
objects
is_object<int(double)>::value is an integral constant expression
that evaluates to false: function types are not
objects
is_object<constvoid>::value
is an integral constant expression that evaluates to false:
void is not an object type
is_object<T>::value_type is the type bool.
is_podtemplate<classT>structis_pod:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
POD type then inherits from true_type,
otherwise inherits from false_type.
POD stands for "Plain old data". Arithmetic types, and enumeration
types, a pointers and pointer to members are all PODs. Classes and unions
can also be POD's if they have no non-static data members that are of reference
or non-POD type, no user defined constructors, no user defined assignment
operators, no private or protected non-static data members, no virtual functions
and no base classes. Finally, a cv-qualified POD is still a POD, as is an
array of PODs.
C++ Standard Reference: 3.9p10 and 9p4 (Note
that POD's are also aggregates, see 8.5.1).
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, ispod
will never report that a class or struct is a POD; this is always safe, if
possibly sub-optimal. Currently (May 2005) only MWCW 9 and Visual C++ 8 have
the necessary compiler-_intrinsics.
Header:#include<boost/type_traits/is_pod.hpp>
or #include<boost/type_traits.hpp>Examples:
is_pod<int>
inherits from true_type.
is_pod<char*>::type is the type true_type.
is_pod<int(*)(long)>::value is an integral constant expression
that evaluates to true.
is_pod<MyClass>::value is an integral constant expression
that evaluates to false.
is_pod<T>::value_type is the type bool.
is_pointeris_pointer is_pointertemplate<classT>structis_pointer:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
pointer type (includes function pointers, but excludes pointers to members)
then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2p2 and 8.3.1.
Header:#include<boost/type_traits/is_pointer.hpp>
or #include<boost/type_traits.hpp>Examples:
is_pointer<int*>
inherits from true_type.
is_pointer<char*const>::type is the type true_type.
is_pointer<int(*)(long)>::value is an integral constant expression
that evaluates to true.
is_pointer<int(MyClass::*)(long)>::value is an integral constant expression
that evaluates to false.
is_pointer<int(MyClass::*)>::value is an integral constant expression
that evaluates to false.
is_pointer<T>::value_type is the type bool.
is_pointer detects "real"
pointer types only, and not smart pointers. Users
should not specialise is_pointer
for smart pointer types, as doing so may cause Boost (and other third party)
code to fail to function correctly. Users wanting a trait to detect smart
pointers should create their own. However, note that there is no way in
general to auto-magically detect smart pointer types, so such a trait would
have to be partially specialised for each supported smart pointer type.
is_polymorphicis_polymorphic is_polymorphictemplate<classT>structis_polymorphic:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
polymorphic type then inherits from true_type,
otherwise inherits from false_type.
Type T must be a complete
type.
C++ Standard Reference: 10.3.
Compiler Compatibility: The implementation
requires some knowledge of the compilers ABI, it does actually seem to work
with the majority of compilers though.
Header:#include<boost/type_traits/is_polymorphic.hpp>
or #include<boost/type_traits.hpp>Examples:
Given: classpoly{virtual~poly();};
is_polymorphic<poly>
inherits from true_type.
is_polymorphic<polyconst>::type
is the type true_type.
is_polymorphic<poly>::value is an integral constant expression
that evaluates to true.
is_polymorphic<T>::value_type is the type bool.
is_sameis_same is_sametemplate<classT,classU>structis_same:publictrue_type-or-false_type{};Inherits: If T and U are the same types
then inherits from true_type,
otherwise inherits from false_type.
Header:#include<boost/type_traits/is_same.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with abstract, incomplete or function types.
Examples:
is_same<int,int>
inherits from true_type.
is_same<int,int>::type is the type true_type.
is_same<int,int>::value is an integral constant expression
that evaluates to true.
is_same<intconst,int>::value
is an integral constant expression that evaluates to false.
is_same<int&,int>::value is an integral constant expression
that evaluates to false.
is_same<T>::value_type is the type bool.
is_scalaris_scalar is_scalartemplate<classT>structis_scalar:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
scalar type then inherits from true_type,
otherwise inherits from false_type.
Scalar types include integral, floating point, enumeration, pointer, and
pointer-to-member types.
C++ Standard Reference: 3.9p10.
Header:#include<boost/type_traits/is_scalar.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Examples:
is_scalar<int*>
inherits from true_type.
is_scalar<int>::type is the type true_type.
is_scalar<double>::value is an integral constant expression
that evaluates to true.
is_scalar<int(*)(long)>::value is an integral constant expression
that evaluates to true.
is_scalar<int(MyClass::*)(long)>::value is an integral constant expression
that evaluates to true.
is_scalar<int(MyClass::*)>::value is an integral constant expression
that evaluates to true.
is_scalar<T>::value_type is the type bool.
is_signedis_signed is_signedtemplate<classT>structis_signed:publictrue_type-or-false_type{};Inherits: If T is an signed integer type
or an enumerated type with an underlying signed integer type, then inherits
from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.1, 7.2.
Header:#include<boost/type_traits/is_signed.hpp>
or #include<boost/type_traits.hpp>Examples:
is_signed<int>
inherits from true_type.
is_signed<intconstvolatile>::type is the type true_type.
is_signed<unsignedint>::value
is an integral constant expression that evaluates to false.
is_signed<myclass>::value is an integral constant expression
that evaluates to false.
is_signed<char>::value is an integral constant expression
whose value depends upon the signedness of type char.
is_signed<longlong>::value
is an integral constant expression that evaluates to true.
is_signed<T>::value_type is the type bool.
is_statelesstemplate<classT>structis_stateless:publictrue_type-or-false_type{};Inherits: Ff T is a stateless type then
inherits from true_type,
otherwise from false_type.
Type T must be a complete type.
A stateless type is a type that has no storage and whose constructors and
destructors are trivial. That means that is_stateless
only inherits from true_type
if the following expression is true:
::boost::has_trivial_constructor<T>::value&&::boost::has_trivial_copy<T>::value&&::boost::has_trivial_destructor<T>::value&&::boost::is_class<T>::value&&::boost::is_empty<T>::valueC++ Standard Reference: 3.9p10.
Header:#include<boost/type_traits/is_stateless.hpp>
or #include<boost/type_traits.hpp>Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
can not be used with function types.
Without some (as yet unspecified) help from the compiler, is_stateless will
never report that a class or struct is stateless; this is always safe, if
possibly sub-optimal. Currently (May 2005) only MWCW 9 and Visual C++ 8 have
the necessary compiler intrinsics
to make this template work automatically.
is_referenceis_reference is_referencetemplate<classT>structis_reference:publictrue_type-or-false_type{};Inherits: If T is a reference pointer type
then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.2 and 8.3.2.
Compiler Compatibility: If the compiler
does not support partial-specialization of class templates, then this template
may report the wrong result for function types, and for types that are both
const and volatile qualified.
Header:#include<boost/type_traits/is_reference.hpp>
or #include<boost/type_traits.hpp>Examples:
is_reference<int&>
inherits from true_type.
is_reference<intconst&>::type
is the type true_type.
is_reference<int(&)(long)>::value is an integral constant expression
that evaluates to true (the argument in this case
is a reference to a function).
is_reference<T>::value_type is the type bool.
is_unionis_union is_uniontemplate<classT>structis_union:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
union type then inherits from true_type,
otherwise inherits from false_type.
Currently requires some kind of compiler support, otherwise unions are identified
as classes.
C++ Standard Reference: 3.9.2 and 9.5.
Compiler Compatibility: Without (some as
yet unspecified) help from the compiler, we cannot distinguish between union
and class types using only standard C++, as a result this type will never
inherit from true_type,
unless the user explicitly specializes the template for their user-defined
union types, or unless the compiler supplies some unspecified intrinsic that
implements this functionality. Currently (May 2005) only Visual C++ 8 has
the necessary compiler intrinsics
to make this trait "just work" without user intervention.
Header:#include<boost/type_traits/is_union.hpp>
or #include<boost/type_traits.hpp>Examples:
is_union<void>
inherits from true_type.
is_union<constvoid>::type
is the type true_type.
is_union<void>::value is an integral constant expression
that evaluates to true.
is_union<void*>::value is an integral constant expression
that evaluates to false.
is_union<T>::value_type is the type bool.
is_unsignedis_unsigned is_unsignedtemplate<classT>structis_unsigned:publictrue_type-or-false_type{};Inherits: If T is an unsigned integer type
or an enumerated type with an underlying unsigned integer type, then inherits
from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.1, 7.2.
Header:#include<boost/type_traits/is_unsigned.hpp>
or #include<boost/type_traits.hpp>Examples:
is_unsigned<unsignedint> inherits from true_type.
is_unsigned<unsignedintconstvolatile>::type
is the type true_type.
is_unsigned<int>::value is an integral constant expression
that evaluates to false.
is_unsigned<myclass>::value is an integral constant expression
that evaluates to false.
is_unsigned<char>::value is an integral constant expression
whose value depends upon the signedness of type char.
is_unsigned<unsignedlonglong>::value is an integral constant expression
that evaluates to true.
is_unsigned<T>::value_type is the type bool.
is_voidis_void is_voidtemplate<classT>structis_void:publictrue_type-or-false_type{};Inherits: If T is a (possibly cv-qualified)
void type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.1p9.
Header:#include<boost/type_traits/is_void.hpp>
or #include<boost/type_traits.hpp>Examples:
is_void<void>
inherits from true_type.
is_void<constvoid>::type
is the type true_type.
is_void<void>::value is an integral constant expression
that evaluates to true.
is_void<void*>::value is an integral constant expression
that evaluates to false.
is_void<T>::value_type is the type bool.
is_volatileis_volatile is_volatiletemplate<classT>structis_volatile:publictrue_type-or-false_type{};Inherits: If T is a (top level) volatile-qualified
type then inherits from true_type,
otherwise inherits from false_type.
C++ Standard Reference: 3.9.3.
Header:#include<boost/type_traits/is_volatile.hpp>
or #include<boost/type_traits.hpp>Examples:
is_volatile<volatileint> inherits from true_type.
is_volatile<constvolatileint>::type is the type true_type.
is_volatile<int*volatile>::value is an integral constant expression
that evaluates to true.
is_volatile<intvolatile*>::value
is an integral constant expression that evaluates to false:
the volatile qualifier is not at the top level in this case.
is_volatile<T>::value_type is the type bool.
make_signedmake_signed make_signedtemplate<classT>structmake_signed{typedefsee-belowtype;};type: If T is a signed integer type then
the same type as T, if T is an unsigned integer type then the corresponding
signed type. Otherwise if T is an enumerated or character type (char or wchar_t)
then a signed integer type with the same width as T.
If T has any cv-qualifiers then these are also present on the result type.
Requires: T must be an integer or enumerated
type, and must not be the type bool.
C++ Standard Reference: 3.9.1.
Header:#include<boost/type_traits/make_signed.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
make_signed<int>::typeintmake_signed<unsignedintconst>::typeintconstmake_signed<constunsignedlonglong>::typeconstlonglongmake_signed<my_enum>::type
A signed integer type with the same width as the enum.
make_signed<wchar_t>::type
A signed integer type with the same width as wchar_t.
make_unsignedmake_unsigned make_unsignedtemplate<classT>structmake_unsigned{typedefsee-belowtype;};type: If T is a unsigned integer type then
the same type as T, if T is an signed integer type then the corresponding
unsigned type. Otherwise if T is an enumerated or character type (char or
wchar_t) then an unsigned integer type with the same width as T.
If T has any cv-qualifiers then these are also present on the result type.
Requires: T must be an integer or enumerated
type, and must not be the type bool.
C++ Standard Reference: 3.9.1.
Header:#include<boost/type_traits/make_unsigned.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
make_signed<int>::typeunsignedintmake_signed<unsignedintconst>::typeunsignedintconstmake_signed<constunsignedlonglong>::typeconstunsignedlonglongmake_signed<my_enum>::type
An unsigned integer type with the same width as the enum.
make_signed<wchar_t>::type
An unsigned integer type with the same width as wchar_t.
promotepromote promotetemplate<classT>structpromote{typedefsee-belowtype;};type: If integral or floating point promotion
can be applied to an rvalue of type T,
then applies integral and floating point promotions to T
and keeps cv-qualifiers of T,
otherwise leaves T unchanged.
See also integral_promotion
and floating_point_promotion.
C++ Standard Reference: 4.5 except 4.5/3
(integral bit-field) and 4.6.
Header:#include<boost/type_traits/promote.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
promote<shortvolatile>::typeintvolatilepromote<floatconst>::typedoubleconstpromote<short&>::typeshort&
integral_constantrankrankintegral_constant ranktemplate<classT>structrank:public integral_constant<std::size_t,RANK(T)>{};Inherits: Class template rank inherits from
integral_constant<std::size_t,RANK(T)>,
where RANK(T) is the
number of array dimensions in type T.
If T is not an array type,
then RANK(T) is zero.
Header:#include<boost/type_traits/rank.hpp>
or #include<boost/type_traits.hpp>Examples:
rank<int[]>
inherits from integral_constant<std::size_t,1>.
rank<double[2][3][4]>::type is the type integral_constant<std::size_t,3>.
rank<int[1]>::value
is an integral constant expression that evaluates to 1.
rank<int[][2]>::value is an integral constant expression
that evaluates to 2.
rank<int*>::value is an integral constant expression
that evaluates to 0.
rank<T>::value_type is the type std::size_t.
remove_all_extentsremove_all_extents remove_all_extentstemplate<classT>structremove_all_extents{typedefsee-belowtype;};type: If T
is an array type, then removes all of the array bounds on T,
otherwise leaves T unchanged.
C++ Standard Reference: 8.3.4.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_all_extents.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_all_extents<int>::typeintremove_all_extents<intconst[2]>::typeintconstremove_all_extents<int[][2]>::typeintremove_all_extents<int[2][3][4]>::typeintremove_all_extents<intconst*>::typeintconst*
remove_constremove_const remove_consttemplate<classT>structremove_const{typedefsee-belowtype;};type: The same type as T,
but with any top level const-qualifier removed.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_const.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_const<int>::typeintremove_const<intconst>::typeintremove_const<intconstvolatile>::typeintvolatileremove_const<intconst&>::typeintconst&remove_const<intconst*>::typeintconst*
remove_cvremove_cv remove_cvtemplate<classT>structremove_cv{typedefsee-belowtype;};type: The same type as T,
but with any top level cv-qualifiers removed.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_cv.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_cv<int>::typeintremove_cv<intconst>::typeintremove_cv<intconstvolatile>::typeintremove_cv<intconst&>::typeintconst&remove_cv<intconst*>::typeintconst*
remove_extentremove_extent remove_extenttemplate<classT>structremove_extent{typedefsee-belowtype;};type: If T
is an array type, then removes the topmost array bound, otherwise leaves
T unchanged.
C++ Standard Reference: 8.3.4.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_extent.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_extent<int>::typeintremove_extent<intconst[2]>::typeintconstremove_extent<int[2][4]>::typeint[4]remove_extent<int[][2]>::typeint[2]remove_extent<intconst*>::typeintconst*
remove_pointerremove_pointer remove_pointertemplate<classT>structremove_pointer{typedefsee-belowtype;};type: The same type as T,
but with any pointer modifier removed.
C++ Standard Reference: 8.3.1.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_pointer.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_pointer<int>::typeintremove_pointer<intconst*>::typeintconstremove_pointer<intconst**>::typeintconst*remove_pointer<int&>::typeint&remove_pointer<int*&>::typeint*&
remove_referenceremove_reference remove_referencetemplate<classT>structremove_reference{typedefsee-belowtype;};type: The same type as T,
but with any reference modifier removed.
C++ Standard Reference: 8.3.2.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_reference.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_reference<int>::typeintremove_reference<intconst&>::typeintconstremove_reference<int*>::typeint*remove_reference<int*&>::typeint*
remove_volatileremove_volatile remove_volatiletemplate<classT>structremove_volatile{typedefsee-belowtype;};type: The same type as T,
but with any top level volatile-qualifier removed.
C++ Standard Reference: 3.9.3.
Compiler Compatibility: If the compiler
does not support partial specialization of class-templates then this template
will compile, but the member type
will always be the same as type T
except where compiler
workarounds have been applied.
Header:#include<boost/type_traits/remove_volatile.hpp>
or #include<boost/type_traits.hpp>
Examples
Expression
Result Type
remove_volatile<int>::typeintremove_volatile<intvolatile>::typeintremove_volatile<intconstvolatile>::typeintconstremove_volatile<intvolatile&>::typeintconst&remove_volatile<intvolatile*>::typeintconst*
type_with_alignmenttype_with_alignment type_with_alignmenttemplate<std::size_tAlign>structtype_with_alignment{typedefsee-belowtype;};type: a built-in or POD type with an alignment
that is a multiple of Align.
Header:#include<boost/type_traits/type_with_alignment.hpp>
or #include<boost/type_traits.hpp> Credits
This documentation was pulled together by John Maddock, using Boost.Quickbook
and Boost.DocBook.
The original version of this library was created by Steve Cleary, Beman Dawes,
Howard Hinnant, and John Maddock. John Maddock is the current maintainer of
the library.
This version of type traits library is based on contributions by Adobe Systems
Inc, David Abrahams, Steve Cleary, Beman Dawes, Aleksey Gurtovoy, Howard Hinnant,
Jesse Jones, Mat Marcus, Itay Maman, John Maddock, Thorsten Ottosen, Robert
Ramey and Jeremy Siek.
Mat Marcus and Jesse Jones invented, and published
a paper describing, the partial specialization workarounds used in
this library.
Aleksey Gurtovoy added MPL integration to the library.
The is_convertible
template is based on code originally devised by Andrei Alexandrescu, see "Generic<Programming>:
Mappings between Types and Values".
The latest version of this library and documentation can be found at www.boost.org. Bugs, suggestions and discussion
should be directed to boost@lists.boost.org (see www.boost.org/more/mailing_lists.htm#main
for subscription details).
This section must not be indexed.template<classT>structadd_const{typedefsee-belowtype;};add_volatileThis section contains one block that must not be indexed and one that should be.This section contains one block that must not be indexed and one that should be.add_volatileThis section contains one block that must not be indexed and one that should be.
template<classT>structadd_const{typedefsee-belowtype;};
template<classT>structadd_volatile{typedefsee-belowtype;};Class IndexTypedef IndexMacro IndexIndex Test 1Index Test 2