annotate DEPENDENCIES/generic/include/boost/units/detail/dimension_impl.hpp @ 125:34e428693f5d vext

Vext -> Repoint
author Chris Cannam
date Thu, 14 Jun 2018 11:15:39 +0100
parents 2665513ce2d3
children
rev   line source
Chris@16 1 // Boost.Units - A C++ library for zero-overhead dimensional analysis and
Chris@16 2 // unit/quantity manipulation and conversion
Chris@16 3 //
Chris@16 4 // Copyright (C) 2003-2008 Matthias Christian Schabel
Chris@16 5 // Copyright (C) 2008 Steven Watanabe
Chris@16 6 //
Chris@16 7 // Distributed under the Boost Software License, Version 1.0. (See
Chris@16 8 // accompanying file LICENSE_1_0.txt or copy at
Chris@16 9 // http://www.boost.org/LICENSE_1_0.txt)
Chris@16 10
Chris@16 11 #ifndef BOOST_UNITS_DIMENSION_IMPL_HPP
Chris@16 12 #define BOOST_UNITS_DIMENSION_IMPL_HPP
Chris@16 13
Chris@16 14 #include <boost/mpl/begin_end.hpp>
Chris@16 15 #include <boost/mpl/deref.hpp>
Chris@16 16 #include <boost/mpl/if.hpp>
Chris@16 17 #include <boost/mpl/list.hpp>
Chris@16 18 #include <boost/mpl/next.hpp>
Chris@16 19 #include <boost/mpl/size.hpp>
Chris@16 20 #include <boost/mpl/less.hpp>
Chris@16 21
Chris@16 22 #include <boost/units/config.hpp>
Chris@16 23 #include <boost/units/dimensionless_type.hpp>
Chris@16 24 #include <boost/units/static_rational.hpp>
Chris@16 25 #include <boost/units/units_fwd.hpp>
Chris@16 26 #include <boost/units/detail/dimension_list.hpp>
Chris@16 27 #include <boost/units/detail/push_front_if.hpp>
Chris@16 28 #include <boost/units/detail/push_front_or_add.hpp>
Chris@16 29
Chris@16 30 /// \file
Chris@16 31 /// \brief Core class and metaprogramming utilities for compile-time dimensional analysis.
Chris@16 32
Chris@16 33 namespace boost {
Chris@16 34
Chris@16 35 namespace units {
Chris@16 36
Chris@16 37 namespace detail {
Chris@16 38
Chris@16 39 template<int N>
Chris@16 40 struct insertion_sort_dims_insert;
Chris@16 41
Chris@16 42 template<bool is_greater>
Chris@16 43 struct insertion_sort_dims_comparison_impl;
Chris@16 44
Chris@16 45 // have to recursively add the element to the next sequence.
Chris@16 46 template<>
Chris@16 47 struct insertion_sort_dims_comparison_impl<true> {
Chris@16 48 template<class Begin, int N, class T>
Chris@16 49 struct apply {
Chris@16 50 typedef list<
Chris@16 51 typename Begin::item,
Chris@16 52 typename insertion_sort_dims_insert<N - 1>::template apply<
Chris@16 53 typename Begin::next,
Chris@16 54 T
Chris@16 55 >::type
Chris@16 56 > type;
Chris@16 57 };
Chris@16 58 };
Chris@16 59
Chris@16 60 // either prepend the current element or join it to
Chris@16 61 // the first remaining element of the sequence.
Chris@16 62 template<>
Chris@16 63 struct insertion_sort_dims_comparison_impl<false> {
Chris@16 64 template<class Begin, int N, class T>
Chris@16 65 struct apply {
Chris@16 66 typedef typename push_front_or_add<Begin, T>::type type;
Chris@16 67 };
Chris@16 68 };
Chris@16 69
Chris@16 70 template<int N>
Chris@16 71 struct insertion_sort_dims_insert {
Chris@16 72 template<class Begin, class T>
Chris@16 73 struct apply {
Chris@16 74 typedef typename insertion_sort_dims_comparison_impl<mpl::less<typename Begin::item, T>::value>::template apply<
Chris@16 75 Begin,
Chris@16 76 N,
Chris@16 77 T
Chris@16 78 >::type type;
Chris@16 79 };
Chris@16 80 };
Chris@16 81
Chris@16 82 template<>
Chris@16 83 struct insertion_sort_dims_insert<0> {
Chris@16 84 template<class Begin, class T>
Chris@16 85 struct apply {
Chris@16 86 typedef list<T, dimensionless_type> type;
Chris@16 87 };
Chris@16 88 };
Chris@16 89
Chris@16 90 template<int N>
Chris@16 91 struct insertion_sort_dims_mpl_sequence {
Chris@16 92 template<class Begin>
Chris@16 93 struct apply {
Chris@16 94 typedef typename insertion_sort_dims_mpl_sequence<N - 1>::template apply<typename mpl::next<Begin>::type>::type next;
Chris@16 95 typedef typename insertion_sort_dims_insert<(next::size::value)>::template apply<next, typename mpl::deref<Begin>::type>::type type;
Chris@16 96 };
Chris@16 97 };
Chris@16 98
Chris@16 99 template<>
Chris@16 100 struct insertion_sort_dims_mpl_sequence<0> {
Chris@16 101 template<class Begin>
Chris@16 102 struct apply {
Chris@16 103 typedef dimensionless_type type;
Chris@16 104 };
Chris@16 105 };
Chris@16 106
Chris@16 107 template<int N>
Chris@16 108 struct insertion_sort_dims_impl {
Chris@16 109 template<class Begin>
Chris@16 110 struct apply {
Chris@16 111 typedef typename insertion_sort_dims_impl<N - 1>::template apply<typename Begin::next>::type next;
Chris@16 112 typedef typename insertion_sort_dims_insert<(next::size::value)>::template apply<next, typename Begin::item>::type type;
Chris@16 113 };
Chris@16 114 };
Chris@16 115
Chris@16 116 template<>
Chris@16 117 struct insertion_sort_dims_impl<0> {
Chris@16 118 template<class Begin>
Chris@16 119 struct apply {
Chris@16 120 typedef dimensionless_type type;
Chris@16 121 };
Chris@16 122 };
Chris@16 123
Chris@16 124 template<class T>
Chris@16 125 struct sort_dims
Chris@16 126 {
Chris@16 127 typedef typename insertion_sort_dims_mpl_sequence<mpl::size<T>::value>::template apply<typename mpl::begin<T>::type>::type type;
Chris@16 128 };
Chris@16 129
Chris@16 130
Chris@16 131 template<class T, class Next>
Chris@16 132 struct sort_dims<list<T, Next> >
Chris@16 133 {
Chris@16 134 typedef typename insertion_sort_dims_impl<list<T, Next>::size::value>::template apply<list<T, Next> >::type type;
Chris@16 135 };
Chris@16 136
Chris@16 137 /// sorted sequences can be merged in linear time
Chris@16 138 template<bool less, bool greater>
Chris@16 139 struct merge_dimensions_func;
Chris@16 140
Chris@16 141 template<int N1, int N2>
Chris@16 142 struct merge_dimensions_impl;
Chris@16 143
Chris@16 144 template<>
Chris@16 145 struct merge_dimensions_func<true, false>
Chris@16 146 {
Chris@16 147 template<typename Begin1, typename Begin2, int N1, int N2>
Chris@16 148 struct apply
Chris@16 149 {
Chris@16 150 typedef list<
Chris@16 151 typename Begin1::item,
Chris@16 152 typename merge_dimensions_impl<N1 - 1, N2>::template apply<
Chris@16 153 typename Begin1::next,
Chris@16 154 Begin2
Chris@16 155 >::type
Chris@16 156 > type;
Chris@16 157 };
Chris@16 158 };
Chris@16 159
Chris@16 160 template<>
Chris@16 161 struct merge_dimensions_func<false, true> {
Chris@16 162 template<typename Begin1, typename Begin2, int N1, int N2>
Chris@16 163 struct apply
Chris@16 164 {
Chris@16 165 typedef list<
Chris@16 166 typename Begin2::item,
Chris@16 167 typename merge_dimensions_impl<N2 - 1, N1>::template apply<
Chris@16 168 typename Begin2::next,
Chris@16 169 Begin1
Chris@16 170 >::type
Chris@16 171 > type;
Chris@16 172 };
Chris@16 173 };
Chris@16 174
Chris@16 175 template<>
Chris@16 176 struct merge_dimensions_func<false, false> {
Chris@16 177 template<typename Begin1, typename Begin2, int N1, int N2>
Chris@16 178 struct apply
Chris@16 179 {
Chris@16 180 typedef typename mpl::plus<typename Begin1::item, typename Begin2::item>::type combined;
Chris@16 181 typedef typename push_front_if<!is_empty_dim<combined>::value>::template apply<
Chris@16 182 typename merge_dimensions_impl<N1 - 1, N2 - 1>::template apply<
Chris@16 183 typename Begin1::next,
Chris@16 184 typename Begin2::next
Chris@16 185 >::type,
Chris@16 186 combined
Chris@16 187 >::type type;
Chris@16 188 };
Chris@16 189 };
Chris@16 190
Chris@16 191 template<int N1, int N2>
Chris@16 192 struct merge_dimensions_impl {
Chris@16 193 template<typename Begin1, typename Begin2>
Chris@16 194 struct apply
Chris@16 195 {
Chris@16 196 typedef typename Begin1::item dim1;
Chris@16 197 typedef typename Begin2::item dim2;
Chris@16 198
Chris@16 199 typedef typename merge_dimensions_func<(mpl::less<dim1,dim2>::value == true),
Chris@16 200 (mpl::less<dim2,dim1>::value == true)>::template apply<
Chris@16 201 Begin1,
Chris@16 202 Begin2,
Chris@16 203 N1,
Chris@16 204 N2
Chris@16 205 >::type type;
Chris@16 206 };
Chris@16 207 };
Chris@16 208
Chris@16 209 template<typename Sequence1, typename Sequence2>
Chris@16 210 struct merge_dimensions
Chris@16 211 {
Chris@16 212 typedef typename detail::merge_dimensions_impl<Sequence1::size::value,
Chris@16 213 Sequence2::size::value>::template
Chris@16 214 apply<
Chris@16 215 Sequence1,
Chris@16 216 Sequence2
Chris@16 217 >::type type;
Chris@16 218 };
Chris@16 219
Chris@16 220 template<int N>
Chris@16 221 struct iterator_to_list
Chris@16 222 {
Chris@16 223 template<typename Begin>
Chris@16 224 struct apply
Chris@16 225 {
Chris@16 226 typedef list<
Chris@16 227 typename Begin::item,
Chris@16 228 typename iterator_to_list<N - 1>::template apply<
Chris@16 229 typename Begin::next
Chris@16 230 >::type
Chris@16 231 > type;
Chris@16 232 };
Chris@16 233 };
Chris@16 234
Chris@16 235 template<>
Chris@16 236 struct iterator_to_list<0>
Chris@16 237 {
Chris@16 238 template<typename Begin>
Chris@16 239 struct apply {
Chris@16 240 typedef dimensionless_type type;
Chris@16 241 };
Chris@16 242 };
Chris@16 243
Chris@16 244 template<int N>
Chris@16 245 struct merge_dimensions_impl<N, 0>
Chris@16 246 {
Chris@16 247 template<typename Begin1, typename Begin2>
Chris@16 248 struct apply
Chris@16 249 {
Chris@16 250 typedef typename iterator_to_list<N>::template apply<Begin1>::type type;
Chris@16 251 };
Chris@16 252 };
Chris@16 253
Chris@16 254 template<int N>
Chris@16 255 struct merge_dimensions_impl<0, N>
Chris@16 256 {
Chris@16 257 template<typename Begin1, typename Begin2>
Chris@16 258 struct apply
Chris@16 259 {
Chris@16 260 typedef typename iterator_to_list<N>::template apply<Begin2>::type type;
Chris@16 261 };
Chris@16 262 };
Chris@16 263
Chris@16 264 template<>
Chris@16 265 struct merge_dimensions_impl<0, 0>
Chris@16 266 {
Chris@16 267 template<typename Begin1, typename Begin2>
Chris@16 268 struct apply
Chris@16 269 {
Chris@16 270 typedef dimensionless_type type;
Chris@16 271 };
Chris@16 272 };
Chris@16 273
Chris@16 274 template<int N>
Chris@16 275 struct static_inverse_impl
Chris@16 276 {
Chris@16 277 template<typename Begin>
Chris@16 278 struct apply {
Chris@16 279 typedef list<
Chris@16 280 typename mpl::negate<typename Begin::item>::type,
Chris@16 281 typename static_inverse_impl<N - 1>::template apply<
Chris@16 282 typename Begin::next
Chris@16 283 >::type
Chris@16 284 > type;
Chris@16 285 };
Chris@16 286 };
Chris@16 287
Chris@16 288 template<>
Chris@16 289 struct static_inverse_impl<0>
Chris@16 290 {
Chris@16 291 template<typename Begin>
Chris@16 292 struct apply
Chris@16 293 {
Chris@16 294 typedef dimensionless_type type;
Chris@16 295 };
Chris@16 296 };
Chris@16 297
Chris@16 298 template<int N>
Chris@16 299 struct static_power_impl
Chris@16 300 {
Chris@16 301 template<typename Begin, typename Ex>
Chris@16 302 struct apply
Chris@16 303 {
Chris@16 304 typedef list<
Chris@16 305 typename mpl::times<typename Begin::item, Ex>::type,
Chris@16 306 typename detail::static_power_impl<N - 1>::template apply<typename Begin::next, Ex>::type
Chris@16 307 > type;
Chris@16 308 };
Chris@16 309 };
Chris@16 310
Chris@16 311 template<>
Chris@16 312 struct static_power_impl<0>
Chris@16 313 {
Chris@16 314 template<typename Begin, typename Ex>
Chris@16 315 struct apply
Chris@16 316 {
Chris@16 317 typedef dimensionless_type type;
Chris@16 318 };
Chris@16 319 };
Chris@16 320
Chris@16 321 template<int N>
Chris@16 322 struct static_root_impl {
Chris@16 323 template<class Begin, class Ex>
Chris@16 324 struct apply {
Chris@16 325 typedef list<
Chris@16 326 typename mpl::divides<typename Begin::item, Ex>::type,
Chris@16 327 typename detail::static_root_impl<N - 1>::template apply<typename Begin::next, Ex>::type
Chris@16 328 > type;
Chris@16 329 };
Chris@16 330 };
Chris@16 331
Chris@16 332 template<>
Chris@16 333 struct static_root_impl<0> {
Chris@16 334 template<class Begin, class Ex>
Chris@16 335 struct apply
Chris@16 336 {
Chris@16 337 typedef dimensionless_type type;
Chris@16 338 };
Chris@16 339 };
Chris@16 340
Chris@16 341 } // namespace detail
Chris@16 342
Chris@16 343 } // namespace units
Chris@16 344
Chris@16 345 } // namespace boost
Chris@16 346
Chris@16 347 #endif // BOOST_UNITS_DIMENSION_IMPL_HPP