C++ Template Metaprogramming
Solutions to the exercises throughout the book
Loading...
Searching...
No Matches
exercise-3-5.hpp
Go to the documentation of this file.
1// ===-- chapter-3/exercise-3-5.hpp ----------------------- -*- C++ -*- --=== //
9#ifndef EXERCISE_3_5
10#define EXERCISE_3_5
11
12#include <boost/static_assert.hpp>
13
14#include <boost/mpl/equal.hpp>
15#include <boost/mpl/transform.hpp>
16#include <boost/mpl/vector_c.hpp>
17
18#include <boost/mpl/placeholders.hpp>
19using namespace boost::mpl::placeholders;
20
21
37namespace exercise_3_5 {
38
40namespace section_3_1 {
41
42// No units!
43typedef boost::mpl::vector_c<int, 0, 0, 0, 0, 0, 0, 0> scalar;
44
45// Simple dimensions
46typedef boost::mpl::vector_c<int, 1, 0, 0, 0, 0, 0, 0> mass;
47typedef boost::mpl::vector_c<int, 0, 1, 0, 0, 0, 0, 0> length;
48typedef boost::mpl::vector_c<int, 0, 0, 1, 0, 0, 0, 0> time;
49typedef boost::mpl::vector_c<int, 0, 0, 0, 1, 0, 0, 0> charge;
50typedef boost::mpl::vector_c<int, 0, 0, 0, 0, 1, 0, 0> temperature;
51typedef boost::mpl::vector_c<int, 0, 0, 0, 0, 0, 1, 0> intensity;
52typedef boost::mpl::vector_c<int, 0, 0, 0, 0, 0, 0, 1> amount_of_substance;
53
54// More complicated units
55typedef boost::mpl::vector_c<int, 0, 1, -1, 0, 0, 0, 0> velocity;
56typedef boost::mpl::vector_c<int, 0, 1, -2, 0, 0, 0, 0> acceleration;
57typedef boost::mpl::vector_c<int, 1, 1, -1, 0, 0, 0, 0> momentum;
58typedef boost::mpl::vector_c<int, 1, 1, -2, 0, 0, 0, 0> force;
59
70template <typename T, typename Dimension>
72{
73public:
78 explicit quantity(T const x)
79 : m_value(x) { }
80
93 template <typename OtherDimension>
95 : m_value(rhs.value())
96 {
98 (boost::mpl::equal<Dimension,OtherDimension>::type::value));
99 }
100
102 T value() const { return m_value; }
103
104private:
107};
108
109// Exercise 3-5 requires the addition of D2, allowing the addition of
110// equivalent matrices with non-directly-convertable types.
111
126template <typename T, typename D1, typename D2>
128{
129 BOOST_STATIC_ASSERT((boost::mpl::equal<D1,D2>::type::value));
130 return quantity<T,D1>(x.value() + y.value());
131}
132
147template <typename T, typename D1, typename D2>
149{
150 return quantity<T,D1>(x.value() - y.value());
151}
152
153// Exercise 3-5: Let's allow multiplication and division of quantities by
154// processing their dimensions.
155
165template<typename D1, typename D2>
167 : boost::mpl::transform<D1,D2,boost::mpl::minus<_1,_2> > { };
168
178template<typename D1, typename D2>
180 : boost::mpl::transform<D1,D2,boost::mpl::plus<_1,_2> > { };
181
195template <typename T, typename D1, typename D2>
198{
200 x.value() * y.value());
201}
202
216template <typename T, typename D1, typename D2>
217quantity<T, typename divide_dimensions<D1,D2>::type>
219{
221 x.value() / y.value());
222}
223
224} // namespace section_3_1
225} // namespace exercise_3_5
226
227#endif // EXERCISE_3_5
BOOST_STATIC_ASSERT((boost::is_same< t5, expected_t5 >::value))
A numerical quanitity with intrinsic dimensions.
T m_value
The current value of this quantity.
T value() const
Return the current quantity's value.
quantity(T const x)
Construct this quantity with an initial value.
quantity(quantity< T, OtherDimension > const &rhs)
Construct a quantity from another quantity with (possibly) different dimensions.
boost::mpl::vector_c< int, 1, 1, -1, 0, 0, 0, 0 > momentum
boost::mpl::vector_c< int, 1, 1, -2, 0, 0, 0, 0 > force
quantity< T, typename multiply_dimensions< D1, D2 >::type > operator*(quantity< T, D1 > const &x, quantity< T, D2 > const &y)
Multiply two quantities.
boost::mpl::vector_c< int, 0, 0, 0, 0, 1, 0, 0 > temperature
boost::mpl::vector_c< int, 0, 0, 1, 0, 0, 0, 0 > time
boost::mpl::vector_c< int, 0, 0, 0, 0, 0, 1, 0 > intensity
boost::mpl::vector_c< int, 0, 1, 0, 0, 0, 0, 0 > length
boost::mpl::vector_c< int, 0, 0, 0, 0, 0, 0, 0 > scalar
boost::mpl::vector_c< int, 0, 1, -1, 0, 0, 0, 0 > velocity
quantity< T, typename divide_dimensions< D1, D2 >::type > operator/(quantity< T, D1 > const &x, quantity< T, D2 > const &y)
Divide two quantities.
quantity< T, D1 > operator+(quantity< T, D1 > const &x, quantity< T, D2 > const &y)
Add two quantities.
boost::mpl::vector_c< int, 0, 0, 0, 1, 0, 0, 0 > charge
quantity< T, D1 > operator-(quantity< T, D1 > const &x, quantity< T, D2 > const &y)
Subtract two quantities.
boost::mpl::vector_c< int, 1, 0, 0, 0, 0, 0, 0 > mass
boost::mpl::vector_c< int, 0, 1, -2, 0, 0, 0, 0 > acceleration
boost::mpl::vector_c< int, 0, 0, 0, 0, 0, 0, 1 > amount_of_substance
Encapsulate solution for Exercise 3-5.
Divide all elements of two dimension sequences.
Multiply all elements of two dimension sequences.