![]() |
Home | Libraries | People | FAQ | More |
By default every entity in Boost.Math lives in namespace boost::math. Defining
the macro BOOST_MATH_NAMESPACE_COMPONENTS
relocates the whole library into a namespace of your choosing. This is intended
for libraries that embed their own copy of Boost.Math (typically in standalone
mode): moving the copy out of boost::math means
it can never collide with a different version of Boost.Math that the end user
also compiles or links against, whether as duplicate symbols in a static library
or as an ODR violation.
#define BOOST_MATH_NAMESPACE_COMPONENTS my_lib, math #include <boost/math/special_functions/gamma.hpp> int main() { double x = my_lib::math::tgamma(5.0); // 24 double y = BOOST_MATH_NAMESPACE::tgamma(5.0); // the same function return x == y ? 0 : 1; }
Nothing changes unless the macro is defined: the default configuration produces exactly the same code as before.
BOOST_MATH_NAMESPACE_COMPONENTS
is a comma separated list of between one and five identifiers, outermost first.
The default is boost,
math. Some examples:
Table 1.1. Example configurations
|
|
Library namespace |
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
The namespace is given as a list of components rather than as a qualified name
such as my_lib::math, because the preprocessor cannot split
a qualified name into its parts, and C++14 (the oldest standard the library
supports) has no nested namespace definitions.
The macro must be defined before the first Boost.Math header is included. In a project with more than one translation unit, set it in the build system so that every translation unit sees the same value:
g++ -DBOOST_MATH_NAMESPACE_COMPONENTS=my_lib,math ... cl /DBOOST_MATH_NAMESPACE_COMPONENTS=my_lib,math ... # CMake target_compile_definitions(my_target PRIVATE BOOST_MATH_NAMESPACE_COMPONENTS=my_lib,math)
<boost/math/tools/config.hpp>
derives the following macros from BOOST_MATH_NAMESPACE_COMPONENTS.
They are always defined, so code that uses them works with any configuration,
including the default one. Defining any of them yourself is a compile time
error.
Table 1.2. Derived macros
|
Macro |
Default expansion |
Description |
|---|---|---|
|
|
|
The qualified name of the library namespace, for example |
|
|
|
Opens the library namespace. Use it only at global namespace scope. |
|
|
|
Closes the namespace opened by |
|
|
|
The number of components, as an integer literal that can be tested
with |
|
|
|
A sibling of the library namespace, formed by appending |
Anything you declare inside the library namespace must follow it when it moves. The usual case is the user_error policy, whose handlers you define inside the policies namespace. Writing them with the macros keeps them correct for every configuration:
BOOST_MATH_NAMESPACE_BEGIN namespace policies { template <class T> T user_domain_error(const char* function, const char* message, const T& val) { // ... } } // namespace policies BOOST_MATH_NAMESPACE_END
The same applies to anything else you previously wrote in namespace
boost {
namespace math
{, such as specializations of library
templates. The convenience macros BOOST_MATH_DECLARE_SPECIAL_FUNCTIONS
and BOOST_MATH_DECLARE_DISTRIBUTIONS
work unchanged in any configuration.
BOOST_MATH_NAMESPACE_COMPONENTS.
boost::math::....
<boost/cstdfloat.hpp> (boost::float64_t
and friends) are not part of boost::math
and stay in namespace boost.
The library's continuous integration builds every public header, plus a runtime
test, with BOOST_MATH_NAMESPACE_COMPONENTS=my_lib,math. It checks that nothing is left in
boost::math and that no symbol in the resulting
binary is in namespace boost.
See libs/math/test/cmake_namespace_test.