I am wanting to use Boost Units for a simulation, but there are a few units I need that aren't in the default systems. For example, slugs (mass). So I have created a custom slug unit that I can instantiate successfully as a quantity. However, when trying to set the conversion factor to kilograms, I get a compilation error.
Here is my header file test.h:
#ifndef DSHELL_TEST_SYSTEM_HPP
#define DSHELL_TEST_SYSTEM_HPP
#include <boost/units/base_dimension.hpp>
#include <boost/units/io.hpp>
#include <boost/units/quantity.hpp>
#include <boost/units/unit.hpp>
#include <boost/units/base_unit.hpp>
#include <boost/units/systems/si/mass.hpp>
using namespace boost::units;
using namespace boost::units::si;
namespace dshell {
namespace units {
struct slug_base_unit : base_unit<slug_base_unit, mass_dimension, 1>
{
static std::string name() { return "slug"; }
static std::string symbol() { return "sl"; }
};
typedef slug_base_unit::unit_type slug_unit;
/// unit constants
BOOST_UNITS_STATIC_CONSTANT(slug, slug_unit);
BOOST_UNITS_STATIC_CONSTANT(slugs, slug_unit);
}
}
BOOST_UNITS_DEFINE_CONVERSION_FACTOR(dshell::units::slug_unit, boost::units::si::mass, double, 14.5939);
#endif // DSHELL_TEST_SYSTEM_HPP
And the main test.cc:
#include <iostream>
#include "test.h"
using namespace dshell::units;
int main () {
quantity<slug_unit> A = 10.0 * slugs;
quantity<mass> B = static_cast<quantity<mass> >(2.0 * slugs);
quantity<mass> C = 2.0 * kilograms;
quantity<mass> D = static_cast<quantity<mass> >(A);
std::cout << A << std::endl;
std::cout << B << std::endl;
std::cout << C << std::endl;
std::cout << D << std::endl;
}
This is the compilation error I get:
In file included from /usr/include/boost/units/conversion.hpp:14,
from /usr/include/boost/units/quantity.hpp:29,
from /usr/include/boost/units/io.hpp:28,
from test.h:5,
from test.cc:3:
/usr/include/boost/units/detail/conversion_impl.hpp: In instantiation of ‘boost::units::detail::call_base_unit_converter_base_unit_impl<false, false>::apply<dshell::units::slug_base_unit, boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > > >’:
/usr/include/boost/units/detail/conversion_impl.hpp:289: instantiated from ‘boost::units::detail::call_base_unit_converter<dshell::units::slug_base_unit, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void> >’
/usr/include/boost/units/detail/conversion_impl.hpp:316: instantiated from ‘boost::units::detail::conversion_impl<1>::apply<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::dimensionless_type> > >’
/usr/include/boost/units/detail/conversion_impl.hpp:445: instantiated from ‘boost::units::detail::conversion_factor_helper<boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void> >’
/usr/include/boost/units/detail/conversion_impl.hpp:40: instantiated from ‘boost::units::detail::conversion_factor_helper<boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void> >’
/usr/include/boost/units/detail/conversion_impl.hpp:345: instantiated from ‘static boost::units::quantity<Unit2, T2> boost::units::conversion_helper<boost::units::quantity<Unit1, T1>, boost::units::quantity<Unit2, T2> >::convert(const boost::units::quantity<Unit1, T1>&) [with Unit1 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, T1 = double, Unit2 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void>, T2 = double]’
/usr/include/boost/units/quantity.hpp:193: instantiated from ‘boost::units::quantity<Unit, Y>::quantity(const boost::units::quantity<Unit2, YY>&, typename boost::disable_if<boost::mpl::and_<typename boost::units::is_implicitly_convertible<Unit2, Unit>::type, boost::units::detail::is_non_narrowing_conversion<YY, Y>, mpl_::bool_<true>, mpl_::bool_<true>, mpl_::bool_<true> >, typename boost::units::detail::disable_if_is_same<Unit, Unit2>::type>::type*) [with Unit2 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, YY = double, Unit = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void>, Y = double]’
test.cc:9: instantiated from here
/usr/include/boost/units/detail/conversion_impl.hpp:202: error: no type named ‘type’ in ‘struct boost::units::detail::conversion_factor_helper<boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void> >’
/usr/include/boost/units/detail/conversion_impl.hpp:203: error: no type named ‘type’ in ‘struct boost::units::detail::conversion_factor_helper<boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void> >’
/usr/include/boost/units/detail/conversion_impl.hpp: In static member function ‘static boost::units::quantity<Unit2, T2> boost::units::conversion_helper<boost::units::quantity<Unit1, T1>, boost::units::quantity<Unit2, T2> >::convert(const boost::units::quantity<Unit1, T1>&) [with Unit1 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, T1 = double, Unit2 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void>, T2 = double]’:
/usr/include/boost/units/quantity.hpp:193: instantiated from ‘boost::units::quantity<Unit, Y>::quantity(const boost::units::quantity<Unit2, YY>&, typename boost::disable_if<boost::mpl::and_<typename boost::units::is_implicitly_convertible<Unit2, Unit>::type, boost::units::detail::is_non_narrowing_conversion<YY, Y>, mpl_::bool_<true>, mpl_::bool_<true>, mpl_::bool_<true> >, typename boost::units::detail::disable_if_is_same<Unit, Unit2>::type>::type*) [with Unit2 = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>, YY = double, Unit = boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void>, Y = double]’
test.cc:9: instantiated from here
/usr/include/boost/units/detail/conversion_impl.hpp:345: error: no matching function for call to ‘conversion_factor(boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::heterogeneous_system<boost::units::heterogeneous_system_impl<boost::units::list<boost::units::heterogeneous_system_dim<dshell::units::slug_base_unit, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::dimensionless_type> >, void>&, boost::units::unit<boost::units::list<boost::units::dim<boost::units::mass_base_dimension, boost::units::static_rational<1l, 1l> >, boost::units::dimensionless_type>, boost::units::homogeneous_system<boost::units::list<boost::units::si::meter_base_unit, boost::units::list<boost::units::scaled_base_unit<boost::units::cgs::gram_base_unit, boost::units::scale<10l, boost::units::static_rational<3l, 1l> > >, boost::units::list<boost::units::si::second_base_unit, boost::units::list<boost::units::si::ampere_base_unit, boost::units::list<boost::units::si::kelvin_base_unit, boost::units::list<boost::units::si::mole_base_unit, boost::units::list<boost::units::si::candela_base_unit, boost::units::list<boost::units::angle::radian_base_unit, boost::units::list<boost::units::angle::steradian_base_unit, boost::units::dimensionless_type> > > > > > > > > >, void>&)’