From cce26ec78ebe71181e2985b2edd037cfdd46c66a Mon Sep 17 00:00:00 2001 From: Tyler Veness Date: Sat, 28 Sep 2019 19:55:50 -0700 Subject: [PATCH] Replace CRLF line endings with LF (#1902) --- wpiutil/src/main/native/include/units/units.h | 9712 ++++++++--------- .../src/main/native/windows/StackWalker.cpp | 2746 ++--- wpiutil/src/main/native/windows/StackWalker.h | 356 +- 3 files changed, 6407 insertions(+), 6407 deletions(-) diff --git a/wpiutil/src/main/native/include/units/units.h b/wpiutil/src/main/native/include/units/units.h index d755446ab7..6b1db1d935 100644 --- a/wpiutil/src/main/native/include/units/units.h +++ b/wpiutil/src/main/native/include/units/units.h @@ -1,4856 +1,4856 @@ -//-------------------------------------------------------------------------------------------------- -// -// Units: A compile-time c++14 unit conversion library with no dependencies -// -//-------------------------------------------------------------------------------------------------- -// -// The MIT License (MIT) -// -// Permission is hereby granted, free of charge, to any person obtaining a copy of this software -// and associated documentation files (the "Software"), to deal in the Software without -// restriction, including without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in all copies or -// substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING -// BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -// -//-------------------------------------------------------------------------------------------------- -// -// Copyright (c) 2016 Nic Holthaus -// -//-------------------------------------------------------------------------------------------------- -// -// ATTRIBUTION: -// Parts of this work have been adapted from: -// http://stackoverflow.com/questions/35069778/create-comparison-trait-for-template-classes-whose-parameters-are-in-a-different -// http://stackoverflow.com/questions/28253399/check-traits-for-all-variadic-template-arguments/28253503 -// http://stackoverflow.com/questions/36321295/rational-approximation-of-square-root-of-stdratio-at-compile-time?noredirect=1#comment60266601_36321295 -// -//-------------------------------------------------------------------------------------------------- -// -/// @file units.h -/// @brief Complete implementation of `units` - a compile-time, header-only, unit conversion -/// library built on c++14 with no dependencies. -// -//-------------------------------------------------------------------------------------------------- - -#pragma once - -#ifndef units_h__ -#define units_h__ - -#ifdef _MSC_VER -# pragma push_macro("pascal") -# undef pascal -# if _MSC_VER <= 1800 -# define _ALLOW_KEYWORD_MACROS -# pragma warning(push) -# pragma warning(disable : 4520) -# pragma push_macro("constexpr") -# define constexpr /*constexpr*/ -# pragma push_macro("noexcept") -# define noexcept throw() -# endif // _MSC_VER < 1800 -#endif // _MSC_VER - -#if !defined(_MSC_VER) || _MSC_VER > 1800 -# define UNIT_HAS_LITERAL_SUPPORT -# define UNIT_HAS_VARIADIC_TEMPLATE_SUPPORT -#endif - -#ifndef UNIT_LIB_DEFAULT_TYPE -# define UNIT_LIB_DEFAULT_TYPE double -#endif - -//-------------------- -// INCLUDES -//-------------------- - -#include -#include -#include -#include -#include -#include - -#if !defined(UNIT_LIB_DISABLE_IOSTREAM) - #include - #include - #include - - //------------------------------ - // STRING FORMATTER - //------------------------------ - - namespace units - { - namespace detail - { - template std::string to_string(const T& t) - { - std::string str{ std::to_string(t) }; - int offset{ 1 }; - - // remove trailing decimal points for integer value units. Locale aware! - struct lconv * lc; - lc = localeconv(); - char decimalPoint = *lc->decimal_point; - if (str.find_last_not_of('0') == str.find(decimalPoint)) { offset = 0; } - str.erase(str.find_last_not_of('0') + offset, std::string::npos); - return str; - } - } - } -#endif - -namespace units -{ - template inline constexpr const char* name(const T&); - template inline constexpr const char* abbreviation(const T&); -} - -//------------------------------ -// MACROS -//------------------------------ - -/** - * @def UNIT_ADD_UNIT_TAGS(namespaceName,nameSingular, namePlural, abbreviation, definition) - * @brief Helper macro for generating the boiler-plate code generating the tags of a new unit. - * @details The macro generates singular, plural, and abbreviated forms - * of the unit definition (e.g. `meter`, `meters`, and `m`), as aliases for the - * unit tag. - * @param namespaceName namespace in which the new units will be encapsulated. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param namePlural - plural version of the unit name, e.g. 'meters' - * @param abbreviation - abbreviated unit name, e.g. 'm' - * @param definition - the variadic parameter is used for the definition of the unit - * (e.g. `unit, units::category::length_unit>`) - * @note a variadic template is used for the definition to allow templates with - * commas to be easily expanded. All the variadic 'arguments' should together - * comprise the unit definition. - */ -#define UNIT_ADD_UNIT_TAGS(namespaceName,nameSingular, namePlural, abbreviation, /*definition*/...)\ - namespace namespaceName\ - {\ - /** @name Units (full names plural) */ /** @{ */ typedef __VA_ARGS__ namePlural; /** @} */\ - /** @name Units (full names singular) */ /** @{ */ typedef namePlural nameSingular; /** @} */\ - /** @name Units (abbreviated) */ /** @{ */ typedef namePlural abbreviation; /** @} */\ - } - -/** - * @def UNIT_ADD_UNIT_DEFINITION(namespaceName,nameSingular) - * @brief Macro for generating the boiler-plate code for the unit_t type definition. - * @details The macro generates the definition of the unit container types, e.g. `meter_t` - * @param namespaceName namespace in which the new units will be encapsulated. - * @param nameSingular singular version of the unit name, e.g. 'meter' - */ -#define UNIT_ADD_UNIT_DEFINITION(namespaceName,nameSingular)\ - namespace namespaceName\ - {\ - /** @name Unit Containers */ /** @{ */ typedef unit_t nameSingular ## _t; /** @} */\ - } - -/** - * @def UNIT_ADD_CUSTOM_TYPE_UNIT_DEFINITION(namespaceName,nameSingular,underlyingType) - * @brief Macro for generating the boiler-plate code for a unit_t type definition with a non-default underlying type. - * @details The macro generates the definition of the unit container types, e.g. `meter_t` - * @param namespaceName namespace in which the new units will be encapsulated. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param underlyingType the underlying type - */ -#define UNIT_ADD_CUSTOM_TYPE_UNIT_DEFINITION(namespaceName,nameSingular, underlyingType)\ - namespace namespaceName\ - {\ - /** @name Unit Containers */ /** @{ */ typedef unit_t nameSingular ## _t; /** @} */\ - } -/** - * @def UNIT_ADD_IO(namespaceName,nameSingular, abbreviation) - * @brief Macro for generating the boiler-plate code needed for I/O for a new unit. - * @details The macro generates the code to insert units into an ostream. It - * prints both the value and abbreviation of the unit when invoked. - * @param namespaceName namespace in which the new units will be encapsulated. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param abbrev - abbreviated unit name, e.g. 'm' - * @note When UNIT_LIB_DISABLE_IOSTREAM is defined, the macro does not generate any code - */ -#if defined(UNIT_LIB_DISABLE_IOSTREAM) - #define UNIT_ADD_IO(namespaceName, nameSingular, abbrev) -#else - #define UNIT_ADD_IO(namespaceName, nameSingular, abbrev)\ - namespace namespaceName\ - {\ - inline std::ostream& operator<<(std::ostream& os, const nameSingular ## _t& obj) \ - {\ - os << obj() << " "#abbrev; return os; \ - }\ - inline std::string to_string(const nameSingular ## _t& obj)\ - {\ - return units::detail::to_string(obj()) + std::string(" "#abbrev);\ - }\ - } -#endif - - /** - * @def UNIT_ADD_NAME(namespaceName,nameSingular,abbreviation) - * @brief Macro for generating constexpr names/abbreviations for units. - * @details The macro generates names for units. E.g. name() of 1_m would be "meter", and - * abbreviation would be "m". - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param abbreviation - abbreviated unit name, e.g. 'm' - */ -#define UNIT_ADD_NAME(namespaceName, nameSingular, abbrev)\ -template<> inline constexpr const char* name(const namespaceName::nameSingular ## _t&)\ -{\ - return #nameSingular;\ -}\ -template<> inline constexpr const char* abbreviation(const namespaceName::nameSingular ## _t&)\ -{\ - return #abbrev;\ -} - -/** - * @def UNIT_ADD_LITERALS(namespaceName,nameSingular,abbreviation) - * @brief Macro for generating user-defined literals for units. - * @details The macro generates user-defined literals for units. A literal suffix is created - * using the abbreviation (e.g. `10.0_m`). - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param abbreviation - abbreviated unit name, e.g. 'm' - * @note When UNIT_HAS_LITERAL_SUPPORT is not defined, the macro does not generate any code - */ -#if defined(UNIT_HAS_LITERAL_SUPPORT) - #define UNIT_ADD_LITERALS(namespaceName, nameSingular, abbreviation)\ - namespace literals\ - {\ - inline constexpr namespaceName::nameSingular ## _t operator""_ ## abbreviation(long double d)\ - {\ - return namespaceName::nameSingular ## _t(static_cast(d));\ - }\ - inline constexpr namespaceName::nameSingular ## _t operator""_ ## abbreviation (unsigned long long d)\ - {\ - return namespaceName::nameSingular ## _t(static_cast(d));\ - }\ - } -#else - #define UNIT_ADD_LITERALS(namespaceName, nameSingular, abbreviation) -#endif - -/** - * @def UNIT_ADD(namespaceName,nameSingular, namePlural, abbreviation, definition) - * @brief Macro for generating the boiler-plate code needed for a new unit. - * @details The macro generates singular, plural, and abbreviated forms - * of the unit definition (e.g. `meter`, `meters`, and `m`), as well as the - * appropriately named unit container (e.g. `meter_t`). A literal suffix is created - * using the abbreviation (e.g. `10.0_m`). It also defines a class-specific - * cout function which prints both the value and abbreviation of the unit when invoked. - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param namePlural - plural version of the unit name, e.g. 'meters' - * @param abbreviation - abbreviated unit name, e.g. 'm' - * @param definition - the variadic parameter is used for the definition of the unit - * (e.g. `unit, units::category::length_unit>`) - * @note a variadic template is used for the definition to allow templates with - * commas to be easily expanded. All the variadic 'arguments' should together - * comprise the unit definition. - */ -#define UNIT_ADD(namespaceName, nameSingular, namePlural, abbreviation, /*definition*/...)\ - UNIT_ADD_UNIT_TAGS(namespaceName,nameSingular, namePlural, abbreviation, __VA_ARGS__)\ - UNIT_ADD_UNIT_DEFINITION(namespaceName,nameSingular)\ - UNIT_ADD_NAME(namespaceName,nameSingular, abbreviation)\ - UNIT_ADD_IO(namespaceName,nameSingular, abbreviation)\ - UNIT_ADD_LITERALS(namespaceName,nameSingular, abbreviation) - -/** - * @def UNIT_ADD_WITH_CUSTOM_TYPE(namespaceName,nameSingular, namePlural, abbreviation, underlyingType, definition) - * @brief Macro for generating the boiler-plate code needed for a new unit with a non-default underlying type. - * @details The macro generates singular, plural, and abbreviated forms - * of the unit definition (e.g. `meter`, `meters`, and `m`), as well as the - * appropriately named unit container (e.g. `meter_t`). A literal suffix is created - * using the abbreviation (e.g. `10.0_m`). It also defines a class-specific - * cout function which prints both the value and abbreviation of the unit when invoked. - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param namePlural - plural version of the unit name, e.g. 'meters' - * @param abbreviation - abbreviated unit name, e.g. 'm' - * @param underlyingType - the underlying type, e.g. 'int' or 'float' - * @param definition - the variadic parameter is used for the definition of the unit - * (e.g. `unit, units::category::length_unit>`) - * @note a variadic template is used for the definition to allow templates with - * commas to be easily expanded. All the variadic 'arguments' should together - * comprise the unit definition. - */ -#define UNIT_ADD_WITH_CUSTOM_TYPE(namespaceName, nameSingular, namePlural, abbreviation, underlyingType, /*definition*/...)\ - UNIT_ADD_UNIT_TAGS(namespaceName,nameSingular, namePlural, abbreviation, __VA_ARGS__)\ - UNIT_ADD_CUSTOM_TYPE_UNIT_DEFINITION(namespaceName,nameSingular,underlyingType)\ - UNIT_ADD_IO(namespaceName,nameSingular, abbreviation)\ - UNIT_ADD_LITERALS(namespaceName,nameSingular, abbreviation) - -/** - * @def UNIT_ADD_DECIBEL(namespaceName, nameSingular, abbreviation) - * @brief Macro to create decibel container and literals for an existing unit type. - * @details This macro generates the decibel unit container, cout overload, and literal definitions. - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the base unit name, e.g. 'watt' - * @param abbreviation - abbreviated decibel unit name, e.g. 'dBW' - */ -#define UNIT_ADD_DECIBEL(namespaceName, nameSingular, abbreviation)\ - namespace namespaceName\ - {\ - /** @name Unit Containers */ /** @{ */ typedef unit_t abbreviation ## _t; /** @} */\ - }\ - UNIT_ADD_IO(namespaceName, abbreviation, abbreviation)\ - UNIT_ADD_LITERALS(namespaceName, abbreviation, abbreviation) - -/** - * @def UNIT_ADD_CATEGORY_TRAIT(unitCategory, baseUnit) - * @brief Macro to create the `is_category_unit` type trait. - * @details This trait allows users to test whether a given type matches - * an intended category. This macro comprises all the boiler-plate - * code necessary to do so. - * @param unitCategory The name of the category of unit, e.g. length or mass. - */ - -#define UNIT_ADD_CATEGORY_TRAIT_DETAIL(unitCategory)\ - namespace traits\ - {\ - /** @cond */\ - namespace detail\ - {\ - template struct is_ ## unitCategory ## _unit_impl : std::false_type {};\ - template\ - struct is_ ## unitCategory ## _unit_impl> : std::is_same>::base_unit_type>, units::category::unitCategory ## _unit>::type {};\ - template class N>\ - struct is_ ## unitCategory ## _unit_impl> : std::is_same>::unit_type>, units::category::unitCategory ## _unit>::type {};\ - }\ - /** @endcond */\ - } - -#if defined(UNIT_HAS_VARIADIC_TEMPLATE_SUPPORT) -#define UNIT_ADD_IS_UNIT_CATEGORY_TRAIT(unitCategory)\ - namespace traits\ - {\ - template struct is_ ## unitCategory ## _unit : std::integral_constant>::value...>::value> {};\ - } -#else -#define UNIT_ADD_IS_UNIT_CATEGORY_TRAIT(unitCategory)\ - namespace traits\ - {\ - template\ - struct is_ ## unitCategory ## _unit : std::integral_constant::type>::value &&\ - units::traits::detail::is_ ## unitCategory ## _unit_impl::type>::value &&\ - units::traits::detail::is_ ## unitCategory ## _unit_impl::type>::value>{};\ - } -#endif - -#define UNIT_ADD_CATEGORY_TRAIT(unitCategory)\ - UNIT_ADD_CATEGORY_TRAIT_DETAIL(unitCategory)\ - /** @ingroup TypeTraits*/\ - /** @brief Trait which tests whether a type represents a unit of unitCategory*/\ - /** @details Inherits from `std::true_type` or `std::false_type`. Use `is_ ## unitCategory ## _unit::value` to test the unit represents a unitCategory quantity.*/\ - /** @tparam T one or more types to test*/\ - UNIT_ADD_IS_UNIT_CATEGORY_TRAIT(unitCategory) - -/** - * @def UNIT_ADD_WITH_METRIC_PREFIXES(nameSingular, namePlural, abbreviation, definition) - * @brief Macro for generating the boiler-plate code needed for a new unit, including its metric - * prefixes from femto to peta. - * @details See UNIT_ADD. In addition to generating the unit definition and containers '(e.g. `meters` and 'meter_t', - * it also creates corresponding units with metric suffixes such as `millimeters`, and `millimeter_t`), as well as the - * literal suffixes (e.g. `10.0_mm`). - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'meter' - * @param namePlural - plural version of the unit name, e.g. 'meters' - * @param abbreviation - abbreviated unit name, e.g. 'm' - * @param definition - the variadic parameter is used for the definition of the unit - * (e.g. `unit, units::category::length_unit>`) - * @note a variadic template is used for the definition to allow templates with - * commas to be easily expanded. All the variadic 'arguments' should together - * comprise the unit definition. - */ -#define UNIT_ADD_WITH_METRIC_PREFIXES(namespaceName, nameSingular, namePlural, abbreviation, /*definition*/...)\ - UNIT_ADD(namespaceName, nameSingular, namePlural, abbreviation, __VA_ARGS__)\ - UNIT_ADD(namespaceName, femto ## nameSingular, femto ## namePlural, f ## abbreviation, femto)\ - UNIT_ADD(namespaceName, pico ## nameSingular, pico ## namePlural, p ## abbreviation, pico)\ - UNIT_ADD(namespaceName, nano ## nameSingular, nano ## namePlural, n ## abbreviation, nano)\ - UNIT_ADD(namespaceName, micro ## nameSingular, micro ## namePlural, u ## abbreviation, micro)\ - UNIT_ADD(namespaceName, milli ## nameSingular, milli ## namePlural, m ## abbreviation, milli)\ - UNIT_ADD(namespaceName, centi ## nameSingular, centi ## namePlural, c ## abbreviation, centi)\ - UNIT_ADD(namespaceName, deci ## nameSingular, deci ## namePlural, d ## abbreviation, deci)\ - UNIT_ADD(namespaceName, deca ## nameSingular, deca ## namePlural, da ## abbreviation, deca)\ - UNIT_ADD(namespaceName, hecto ## nameSingular, hecto ## namePlural, h ## abbreviation, hecto)\ - UNIT_ADD(namespaceName, kilo ## nameSingular, kilo ## namePlural, k ## abbreviation, kilo)\ - UNIT_ADD(namespaceName, mega ## nameSingular, mega ## namePlural, M ## abbreviation, mega)\ - UNIT_ADD(namespaceName, giga ## nameSingular, giga ## namePlural, G ## abbreviation, giga)\ - UNIT_ADD(namespaceName, tera ## nameSingular, tera ## namePlural, T ## abbreviation, tera)\ - UNIT_ADD(namespaceName, peta ## nameSingular, peta ## namePlural, P ## abbreviation, peta)\ - - /** - * @def UNIT_ADD_WITH_METRIC_AND_BINARY_PREFIXES(nameSingular, namePlural, abbreviation, definition) - * @brief Macro for generating the boiler-plate code needed for a new unit, including its metric - * prefixes from femto to peta, and binary prefixes from kibi to exbi. - * @details See UNIT_ADD. In addition to generating the unit definition and containers '(e.g. `bytes` and 'byte_t', - * it also creates corresponding units with metric suffixes such as `millimeters`, and `millimeter_t`), as well as the - * literal suffixes (e.g. `10.0_B`). - * @param namespaceName namespace in which the new units will be encapsulated. All literal values - * are placed in the `units::literals` namespace. - * @param nameSingular singular version of the unit name, e.g. 'byte' - * @param namePlural - plural version of the unit name, e.g. 'bytes' - * @param abbreviation - abbreviated unit name, e.g. 'B' - * @param definition - the variadic parameter is used for the definition of the unit - * (e.g. `unit, units::category::data_unit>`) - * @note a variadic template is used for the definition to allow templates with - * commas to be easily expanded. All the variadic 'arguments' should together - * comprise the unit definition. - */ -#define UNIT_ADD_WITH_METRIC_AND_BINARY_PREFIXES(namespaceName, nameSingular, namePlural, abbreviation, /*definition*/...)\ - UNIT_ADD_WITH_METRIC_PREFIXES(namespaceName, nameSingular, namePlural, abbreviation, __VA_ARGS__)\ - UNIT_ADD(namespaceName, kibi ## nameSingular, kibi ## namePlural, Ki ## abbreviation, kibi)\ - UNIT_ADD(namespaceName, mebi ## nameSingular, mebi ## namePlural, Mi ## abbreviation, mebi)\ - UNIT_ADD(namespaceName, gibi ## nameSingular, gibi ## namePlural, Gi ## abbreviation, gibi)\ - UNIT_ADD(namespaceName, tebi ## nameSingular, tebi ## namePlural, Ti ## abbreviation, tebi)\ - UNIT_ADD(namespaceName, pebi ## nameSingular, pebi ## namePlural, Pi ## abbreviation, pebi)\ - UNIT_ADD(namespaceName, exbi ## nameSingular, exbi ## namePlural, Ei ## abbreviation, exbi) - -//-------------------- -// UNITS NAMESPACE -//-------------------- - -/** - * @namespace units - * @brief Unit Conversion Library namespace - */ -namespace units -{ - //---------------------------------- - // DOXYGEN - //---------------------------------- - - /** - * @defgroup UnitContainers Unit Containers - * @brief Defines a series of classes which contain dimensioned values. Unit containers - * store a value, and support various arithmetic operations. - */ - - /** - * @defgroup UnitTypes Unit Types - * @brief Defines a series of classes which represent units. These types are tags used by - * the conversion function, to create compound units, or to create `unit_t` types. - * By themselves, they are not containers and have no stored value. - */ - - /** - * @defgroup UnitManipulators Unit Manipulators - * @brief Defines a series of classes used to manipulate unit types, such as `inverse<>`, `squared<>`, and metric prefixes. - * Unit manipulators can be chained together, e.g. `inverse>>` to - * represent picoseconds^-2. - */ - - /** - * @defgroup CompileTimeUnitManipulators Compile-time Unit Manipulators - * @brief Defines a series of classes used to manipulate `unit_value_t` types at compile-time, such as `unit_value_add<>`, `unit_value_sqrt<>`, etc. - * Compile-time manipulators can be chained together, e.g. `unit_value_sqrt, unit_value_power>>` to - * represent `c = sqrt(a^2 + b^2). - */ - - /** - * @defgroup UnitMath Unit Math - * @brief Defines a collection of unit-enabled, strongly-typed versions of `` functions. - * @details Includes most c++11 extensions. - */ - - /** - * @defgroup Conversion Explicit Conversion - * @brief Functions used to convert values of one logical type to another. - */ - - /** - * @defgroup TypeTraits Type Traits - * @brief Defines a series of classes to obtain unit type information at compile-time. - */ - - //------------------------------ - // FORWARD DECLARATIONS - //------------------------------ - - /** @cond */ // DOXYGEN IGNORE - namespace constants - { - namespace detail - { - static constexpr const UNIT_LIB_DEFAULT_TYPE PI_VAL = 3.14159265358979323846264338327950288419716939937510; - } - } - /** @endcond */ // END DOXYGEN IGNORE - - //------------------------------ - // RATIO TRAITS - //------------------------------ - - /** - * @ingroup TypeTraits - * @{ - */ - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /// has_num implementation. - template - struct has_num_impl - { - template - static constexpr auto test(U*)->std::is_integral {return std::is_integral{}; } - template - static constexpr std::false_type test(...) { return std::false_type{}; } - - using type = decltype(test(0)); - }; - } - - /** - * @brief Trait which checks for the existence of a static numerator. - * @details Inherits from `std::true_type` or `std::false_type`. Use `has_num::value` to test - * whether `class T` has a numerator static member. - */ - template - struct has_num : units::detail::has_num_impl::type {}; - - namespace detail - { - /// has_den implementation. - template - struct has_den_impl - { - template - static constexpr auto test(U*)->std::is_integral { return std::is_integral{}; } - template - static constexpr std::false_type test(...) { return std::false_type{}; } - - using type = decltype(test(0)); - }; - } - - /** - * @brief Trait which checks for the existence of a static denominator. - * @details Inherits from `std::true_type` or `std::false_type`. Use `has_den::value` to test - * whether `class T` has a denominator static member. - */ - template - struct has_den : units::detail::has_den_impl::type {}; - - /** @endcond */ // END DOXYGEN IGNORE - - namespace traits - { - /** - * @brief Trait that tests whether a type represents a std::ratio. - * @details Inherits from `std::true_type` or `std::false_type`. Use `is_ratio::value` to test - * whether `class T` implements a std::ratio. - */ - template - struct is_ratio : std::integral_constant::value && - has_den::value> - {}; - } - - //------------------------------ - // UNIT TRAITS - //------------------------------ - - /** @cond */ // DOXYGEN IGNORE - /** - * @brief void type. - * @details Helper class for creating type traits. - */ - template - struct void_t { typedef void type; }; - - /** - * @brief parameter pack for boolean arguments. - */ - template struct bool_pack {}; - - /** - * @brief Trait which tests that a set of other traits are all true. - */ - template - struct all_true : std::is_same, units::bool_pack> {}; - /** @endcond */ // DOXYGEN IGNORE - - /** - * @brief namespace representing type traits which can access the properties of types provided by the units library. - */ - namespace traits - { -#ifdef FOR_DOXYGEN_PURPOSES_ONLY - /** - * @ingroup TypeTraits - * @brief Traits class defining the properties of units. - * @details The units library determines certain properties of the units passed to - * them and what they represent by using the members of the corresponding - * unit_traits instantiation. - */ - template - struct unit_traits - { - typedef typename T::base_unit_type base_unit_type; ///< Unit type that the unit was derived from. May be a `base_unit` or another `unit`. Use the `base_unit_of` trait to find the SI base unit type. This will be `void` if type `T` is not a unit. - typedef typename T::conversion_ratio conversion_ratio; ///< `std::ratio` representing the conversion factor to the `base_unit_type`. This will be `void` if type `T` is not a unit. - typedef typename T::pi_exponent_ratio pi_exponent_ratio; ///< `std::ratio` representing the exponent of pi to be used in the conversion. This will be `void` if type `T` is not a unit. - typedef typename T::translation_ratio translation_ratio; ///< `std::ratio` representing a datum translation to the base unit (i.e. degrees C to degrees F conversion). This will be `void` if type `T` is not a unit. - }; -#endif - /** @cond */ // DOXYGEN IGNORE - /** - * @brief unit traits implementation for classes which are not units. - */ - template - struct unit_traits - { - typedef void base_unit_type; - typedef void conversion_ratio; - typedef void pi_exponent_ratio; - typedef void translation_ratio; - }; - - template - struct unit_traits - ::type> - { - typedef typename T::base_unit_type base_unit_type; ///< Unit type that the unit was derived from. May be a `base_unit` or another `unit`. Use the `base_unit_of` trait to find the SI base unit type. This will be `void` if type `T` is not a unit. - typedef typename T::conversion_ratio conversion_ratio; ///< `std::ratio` representing the conversion factor to the `base_unit_type`. This will be `void` if type `T` is not a unit. - typedef typename T::pi_exponent_ratio pi_exponent_ratio; ///< `std::ratio` representing the exponent of pi to be used in the conversion. This will be `void` if type `T` is not a unit. - typedef typename T::translation_ratio translation_ratio; ///< `std::ratio` representing a datum translation to the base unit (i.e. degrees C to degrees F conversion). This will be `void` if type `T` is not a unit. - }; - /** @endcond */ // END DOXYGEN IGNORE - } - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief helper type to identify base units. - * @details A non-templated base class for `base_unit` which enables RTTI testing. - */ - struct _base_unit_t {}; - } - /** @endcond */ // END DOXYGEN IGNORE - - namespace traits - { - /** - * @ingroup TypeTraits - * @brief Trait which tests if a class is a `base_unit` type. - * @details Inherits from `std::true_type` or `std::false_type`. Use `is_base_unit::value` to test - * whether `class T` implements a `base_unit`. - */ - template - struct is_base_unit : std::is_base_of {}; - } - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief helper type to identify units. - * @details A non-templated base class for `unit` which enables RTTI testing. - */ - struct _unit {}; - - template - using meter_ratio = std::ratio; - } - /** @endcond */ // END DOXYGEN IGNORE - - namespace traits - { - /** - * @ingroup TypeTraits - * @brief Traits which tests if a class is a `unit` - * @details Inherits from `std::true_type` or `std::false_type`. Use `is_unit::value` to test - * whether `class T` implements a `unit`. - */ - template - struct is_unit : std::is_base_of::type {}; - } - - /** @} */ // end of TypeTraits - - //------------------------------ - // BASE UNIT CLASS - //------------------------------ - - /** - * @ingroup UnitTypes - * @brief Class representing SI base unit types. - * @details Base units are represented by a combination of `std::ratio` template parameters, each - * describing the exponent of the type of unit they represent. Example: meters per second - * would be described by a +1 exponent for meters, and a -1 exponent for seconds, thus: - * `base_unit, std::ratio<0>, std::ratio<-1>>` - * @tparam Meter `std::ratio` representing the exponent value for meters. - * @tparam Kilogram `std::ratio` representing the exponent value for kilograms. - * @tparam Second `std::ratio` representing the exponent value for seconds. - * @tparam Radian `std::ratio` representing the exponent value for radians. Although radians are not SI base units, they are included because radians are described by the SI as m * m^-1, which would make them indistinguishable from scalars. - * @tparam Ampere `std::ratio` representing the exponent value for amperes. - * @tparam Kelvin `std::ratio` representing the exponent value for Kelvin. - * @tparam Mole `std::ratio` representing the exponent value for moles. - * @tparam Candela `std::ratio` representing the exponent value for candelas. - * @tparam Byte `std::ratio` representing the exponent value for bytes. - * @sa category for type aliases for SI base_unit types. - */ - template, - class Kilogram = std::ratio<0>, - class Second = std::ratio<0>, - class Radian = std::ratio<0>, - class Ampere = std::ratio<0>, - class Kelvin = std::ratio<0>, - class Mole = std::ratio<0>, - class Candela = std::ratio<0>, - class Byte = std::ratio<0>> - struct base_unit : units::detail::_base_unit_t - { - static_assert(traits::is_ratio::value, "Template parameter `Meter` must be a `std::ratio` representing the exponent of meters the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Kilogram` must be a `std::ratio` representing the exponent of kilograms the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Second` must be a `std::ratio` representing the exponent of seconds the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Ampere` must be a `std::ratio` representing the exponent of amperes the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Kelvin` must be a `std::ratio` representing the exponent of kelvin the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Candela` must be a `std::ratio` representing the exponent of candelas the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Mole` must be a `std::ratio` representing the exponent of moles the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Radian` must be a `std::ratio` representing the exponent of radians the unit has"); - static_assert(traits::is_ratio::value, "Template parameter `Byte` must be a `std::ratio` representing the exponent of bytes the unit has"); - - typedef Meter meter_ratio; - typedef Kilogram kilogram_ratio; - typedef Second second_ratio; - typedef Radian radian_ratio; - typedef Ampere ampere_ratio; - typedef Kelvin kelvin_ratio; - typedef Mole mole_ratio; - typedef Candela candela_ratio; - typedef Byte byte_ratio; - }; - - //------------------------------ - // UNIT CATEGORIES - //------------------------------ - - /** - * @brief namespace representing the implemented base and derived unit types. These will not generally be needed by library users. - * @sa base_unit for the definition of the category parameters. - */ - namespace category - { - // SCALAR (DIMENSIONLESS) TYPES - typedef base_unit<> scalar_unit; ///< Represents a quantity with no dimension. - typedef base_unit<> dimensionless_unit; ///< Represents a quantity with no dimension. - - // SI BASE UNIT TYPES - // METERS KILOGRAMS SECONDS RADIANS AMPERES KELVIN MOLE CANDELA BYTE --- CATEGORY - typedef base_unit> length_unit; ///< Represents an SI base unit of length - typedef base_unit, std::ratio<1>> mass_unit; ///< Represents an SI base unit of mass - typedef base_unit, std::ratio<0>, std::ratio<1>> time_unit; ///< Represents an SI base unit of time - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<1>> angle_unit; ///< Represents an SI base unit of angle - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> current_unit; ///< Represents an SI base unit of current - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> temperature_unit; ///< Represents an SI base unit of temperature - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> substance_unit; ///< Represents an SI base unit of amount of substance - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> luminous_intensity_unit; ///< Represents an SI base unit of luminous intensity - - // SI DERIVED UNIT TYPES - // METERS KILOGRAMS SECONDS RADIANS AMPERES KELVIN MOLE CANDELA BYTE --- CATEGORY - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<2>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>> solid_angle_unit; ///< Represents an SI derived unit of solid angle - typedef base_unit, std::ratio<0>, std::ratio<-1>> frequency_unit; ///< Represents an SI derived unit of frequency - typedef base_unit, std::ratio<0>, std::ratio<-1>> velocity_unit; ///< Represents an SI derived unit of velocity - typedef base_unit, std::ratio<0>, std::ratio<-1>, std::ratio<1>> angular_velocity_unit; ///< Represents an SI derived unit of angular velocity - typedef base_unit, std::ratio<0>, std::ratio<-2>> acceleration_unit; ///< Represents an SI derived unit of acceleration - typedef base_unit, std::ratio<1>, std::ratio<-2>> force_unit; ///< Represents an SI derived unit of force - typedef base_unit, std::ratio<1>, std::ratio<-2>> pressure_unit; ///< Represents an SI derived unit of pressure - typedef base_unit, std::ratio<0>, std::ratio<1>, std::ratio<0>, std::ratio<1>> charge_unit; ///< Represents an SI derived unit of charge - typedef base_unit, std::ratio<1>, std::ratio<-2>> energy_unit; ///< Represents an SI derived unit of energy - typedef base_unit, std::ratio<1>, std::ratio<-3>> power_unit; ///< Represents an SI derived unit of power - typedef base_unit, std::ratio<1>, std::ratio<-3>, std::ratio<0>, std::ratio<-1>> voltage_unit; ///< Represents an SI derived unit of voltage - typedef base_unit, std::ratio<-1>, std::ratio<4>, std::ratio<0>, std::ratio<2>> capacitance_unit; ///< Represents an SI derived unit of capacitance - typedef base_unit, std::ratio<1>, std::ratio<-3>, std::ratio<0>, std::ratio<-2>> impedance_unit; ///< Represents an SI derived unit of impedance - typedef base_unit, std::ratio<-1>, std::ratio<3>, std::ratio<0>, std::ratio<2>> conductance_unit; ///< Represents an SI derived unit of conductance - typedef base_unit, std::ratio<1>, std::ratio<-2>, std::ratio<0>, std::ratio<-1>> magnetic_flux_unit; ///< Represents an SI derived unit of magnetic flux - typedef base_unit, std::ratio<1>, std::ratio<-2>, std::ratio<0>, std::ratio<-1>> magnetic_field_strength_unit; ///< Represents an SI derived unit of magnetic field strength - typedef base_unit, std::ratio<1>, std::ratio<-2>, std::ratio<0>, std::ratio<-2>> inductance_unit; ///< Represents an SI derived unit of inductance - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<2>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> luminous_flux_unit; ///< Represents an SI derived unit of luminous flux - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<2>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> illuminance_unit; ///< Represents an SI derived unit of illuminance - typedef base_unit, std::ratio<0>, std::ratio<-1>> radioactivity_unit; ///< Represents an SI derived unit of radioactivity - - // OTHER UNIT TYPES - // METERS KILOGRAMS SECONDS RADIANS AMPERES KELVIN MOLE CANDELA BYTE --- CATEGORY - typedef base_unit, std::ratio<1>, std::ratio<-2>> torque_unit; ///< Represents an SI derived unit of torque - typedef base_unit> area_unit; ///< Represents an SI derived unit of area - typedef base_unit> volume_unit; ///< Represents an SI derived unit of volume - typedef base_unit, std::ratio<1>> density_unit; ///< Represents an SI derived unit of density - typedef base_unit<> concentration_unit; ///< Represents a unit of concentration - typedef base_unit, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> data_unit; ///< Represents a unit of data size - typedef base_unit, std::ratio<0>, std::ratio<-1>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<1>> data_transfer_rate_unit; ///< Represents a unit of data transfer rate - } - - //------------------------------ - // UNIT CLASSES - //------------------------------ - - /** @cond */ // DOXYGEN IGNORE - /** - * @brief unit type template specialization for units derived from base units. - */ - template struct unit; - template - struct unit, PiExponent, Translation> : units::detail::_unit - { - static_assert(traits::is_ratio::value, "Template parameter `Conversion` must be a `std::ratio` representing the conversion factor to `BaseUnit`."); - static_assert(traits::is_ratio::value, "Template parameter `PiExponent` must be a `std::ratio` representing the exponents of Pi the unit has."); - static_assert(traits::is_ratio::value, "Template parameter `Translation` must be a `std::ratio` representing an additive translation required by the unit conversion."); - - typedef typename units::base_unit base_unit_type; - typedef Conversion conversion_ratio; - typedef Translation translation_ratio; - typedef PiExponent pi_exponent_ratio; - }; - /** @endcond */ // END DOXYGEN IGNORE - - /** - * @brief Type representing an arbitrary unit. - * @ingroup UnitTypes - * @details `unit` types are used as tags for the `conversion` function. They are *not* containers - * (see `unit_t` for a container class). Each unit is defined by: - * - * - A `std::ratio` defining the conversion factor to the base unit type. (e.g. `std::ratio<1,12>` for inches to feet) - * - A base unit that the unit is derived from (or a unit category. Must be of type `unit` or `base_unit`) - * - An exponent representing factors of PI required by the conversion. (e.g. `std::ratio<-1>` for a radians to degrees conversion) - * - a ratio representing a datum translation required for the conversion (e.g. `std::ratio<32>` for a farenheit to celsius conversion) - * - * Typically, a specific unit, like `meters`, would be implemented as a type alias - * of `unit`, i.e. `using meters = unit, units::category::length_unit`, or - * `using inches = unit, feet>`. - * @tparam Conversion std::ratio representing scalar multiplication factor. - * @tparam BaseUnit Unit type which this unit is derived from. May be a `base_unit`, or another `unit`. - * @tparam PiExponent std::ratio representing the exponent of pi required by the conversion. - * @tparam Translation std::ratio representing any datum translation required by the conversion. - */ - template, class Translation = std::ratio<0>> - struct unit : units::detail::_unit - { - static_assert(traits::is_unit::value, "Template parameter `BaseUnit` must be a `unit` type."); - static_assert(traits::is_ratio::value, "Template parameter `Conversion` must be a `std::ratio` representing the conversion factor to `BaseUnit`."); - static_assert(traits::is_ratio::value, "Template parameter `PiExponent` must be a `std::ratio` representing the exponents of Pi the unit has."); - - typedef typename units::traits::unit_traits::base_unit_type base_unit_type; - typedef typename std::ratio_multiply conversion_ratio; - typedef typename std::ratio_add pi_exponent_ratio; - typedef typename std::ratio_add, typename BaseUnit::translation_ratio> translation_ratio; - }; - - //------------------------------ - // BASE UNIT MANIPULATORS - //------------------------------ - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief base_unit_of trait implementation - * @details recursively seeks base_unit type that a unit is derived from. Since units can be - * derived from other units, the `base_unit_type` typedef may not represent this value. - */ - template struct base_unit_of_impl; - template - struct base_unit_of_impl> : base_unit_of_impl {}; - template - struct base_unit_of_impl> - { - typedef base_unit type; - }; - template<> - struct base_unit_of_impl - { - typedef void type; - }; - } - /** @endcond */ // END DOXYGEN IGNORE - - namespace traits - { - /** - * @brief Trait which returns the `base_unit` type that a unit is originally derived from. - * @details Since units can be derived from other `unit` types in addition to `base_unit` types, - * the `base_unit_type` typedef will not always be a `base_unit` (or unit category). - * Since compatible - */ - template - using base_unit_of = typename units::detail::base_unit_of_impl::type; - } - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief implementation of base_unit_multiply - * @details 'multiples' (adds exponent ratios of) two base unit types. Base units can be found - * using `base_unit_of`. - */ - template struct base_unit_multiply_impl; - template - struct base_unit_multiply_impl, base_unit> { - using type = base_unit...>; - }; - - /** - * @brief represents type of two base units multiplied together - */ - template - using base_unit_multiply = typename base_unit_multiply_impl::type; - - /** - * @brief implementation of base_unit_divide - * @details 'dived' (subtracts exponent ratios of) two base unit types. Base units can be found - * using `base_unit_of`. - */ - template struct base_unit_divide_impl; - template - struct base_unit_divide_impl, base_unit> { - using type = base_unit...>; - }; - - /** - * @brief represents the resulting type of `base_unit` U1 divided by U2. - */ - template - using base_unit_divide = typename base_unit_divide_impl::type; - - /** - * @brief implementation of inverse_base - * @details multiplies all `base_unit` exponent ratios by -1. The resulting type represents - * the inverse base unit of the given `base_unit` type. - */ - template struct inverse_base_impl; - - template - struct inverse_base_impl> { - using type = base_unit>...>; - }; - - /** - * @brief represent the inverse type of `class U` - * @details E.g. if `U` is `length_unit`, then `inverse` will represent `length_unit^-1`. - */ - template using inverse_base = typename inverse_base_impl::type; - - /** - * @brief implementation of `squared_base` - * @details multiplies all the exponent ratios of the given class by 2. The resulting type is - * equivalent to the given type squared. - */ - template struct squared_base_impl; - template - struct squared_base_impl> { - using type = base_unit>...>; - }; - - /** - * @brief represents the type of a `base_unit` squared. - * @details E.g. `squared` will represent `length_unit^2`. - */ - template using squared_base = typename squared_base_impl::type; - - /** - * @brief implementation of `cubed_base` - * @details multiplies all the exponent ratios of the given class by 3. The resulting type is - * equivalent to the given type cubed. - */ - template struct cubed_base_impl; - template - struct cubed_base_impl> { - using type = base_unit>...>; - }; - - /** - * @brief represents the type of a `base_unit` cubed. - * @details E.g. `cubed` will represent `length_unit^3`. - */ - template using cubed_base = typename cubed_base_impl::type; - - /** - * @brief implementation of `sqrt_base` - * @details divides all the exponent ratios of the given class by 2. The resulting type is - * equivalent to the square root of the given type. - */ - template struct sqrt_base_impl; - template - struct sqrt_base_impl> { - using type = base_unit>...>; - }; - - /** - * @brief represents the square-root type of a `base_unit`. - * @details E.g. `sqrt` will represent `length_unit^(1/2)`. - */ - template using sqrt_base = typename sqrt_base_impl::type; - - /** - * @brief implementation of `cbrt_base` - * @details divides all the exponent ratios of the given class by 3. The resulting type is - * equivalent to the given type's cube-root. - */ - template struct cbrt_base_impl; - template - struct cbrt_base_impl> { - using type = base_unit>...>; - }; - - /** - * @brief represents the cube-root type of a `base_unit` . - * @details E.g. `cbrt` will represent `length_unit^(1/3)`. - */ - template using cbrt_base = typename cbrt_base_impl::type; - } - /** @endcond */ // END DOXYGEN IGNORE - - //------------------------------ - // UNIT MANIPULATORS - //------------------------------ - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief implementation of `unit_multiply`. - * @details multiplies two units. The base unit becomes the base units of each with their exponents - * added together. The conversion factors of each are multiplied by each other. Pi exponent ratios - * are added, and datum translations are removed. - */ - template - struct unit_multiply_impl - { - using type = unit < std::ratio_multiply, - base_unit_multiply , traits::base_unit_of>, - std::ratio_add, - std::ratio < 0 >> ; - }; - - /** - * @brief represents the type of two units multiplied together. - * @details recalculates conversion and exponent ratios at compile-time. - */ - template - using unit_multiply = typename unit_multiply_impl::type; - - /** - * @brief implementation of `unit_divide`. - * @details divides two units. The base unit becomes the base units of each with their exponents - * subtracted from each other. The conversion factors of each are divided by each other. Pi exponent ratios - * are subtracted, and datum translations are removed. - */ - template - struct unit_divide_impl - { - using type = unit < std::ratio_divide, - base_unit_divide, traits::base_unit_of>, - std::ratio_subtract, - std::ratio < 0 >> ; - }; - - /** - * @brief represents the type of two units divided by each other. - * @details recalculates conversion and exponent ratios at compile-time. - */ - template - using unit_divide = typename unit_divide_impl::type; - - /** - * @brief implementation of `inverse` - * @details inverts a unit (equivalent to 1/unit). The `base_unit` and pi exponents are all multiplied by - * -1. The conversion ratio numerator and denominator are swapped. Datum translation - * ratios are removed. - */ - template - struct inverse_impl - { - using type = unit < std::ratio, - inverse_base::base_unit_type>>, - std::ratio_multiply::pi_exponent_ratio, std::ratio<-1>>, - std::ratio < 0 >> ; // inverses are rates or change, the translation factor goes away. - }; - } - /** @endcond */ // END DOXYGEN IGNORE - - /** - * @brief represents the inverse unit type of `class U`. - * @ingroup UnitManipulators - * @tparam U `unit` type to invert. - * @details E.g. `inverse` will represent meters^-1 (i.e. 1/meters). - */ - template using inverse = typename units::detail::inverse_impl::type; - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief implementation of `squared` - * @details Squares the conversion ratio, `base_unit` exponents, pi exponents, and removes - * datum translation ratios. - */ - template - struct squared_impl - { - static_assert(traits::is_unit::value, "Template parameter `Unit` must be a `unit` type."); - using Conversion = typename Unit::conversion_ratio; - using type = unit < std::ratio_multiply, - squared_base>, - std::ratio_multiply>, - typename Unit::translation_ratio - > ; - }; - } - /** @endcond */ // END DOXYGEN IGNORE - - /** - * @brief represents the unit type of `class U` squared - * @ingroup UnitManipulators - * @tparam U `unit` type to square. - * @details E.g. `square` will represent meters^2. - */ - template - using squared = typename units::detail::squared_impl::type; - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - /** - * @brief implementation of `cubed` - * @details Cubes the conversion ratio, `base_unit` exponents, pi exponents, and removes - * datum translation ratios. - */ - template - struct cubed_impl - { - static_assert(traits::is_unit::value, "Template parameter `Unit` must be a `unit` type."); - using Conversion = typename Unit::conversion_ratio; - using type = unit < std::ratio_multiply>, - cubed_base>, - std::ratio_multiply>, - typename Unit::translation_ratio> ; - }; - } - /** @endcond */ // END DOXYGEN IGNORE - - /** - * @brief represents the type of `class U` cubed. - * @ingroup UnitManipulators - * @tparam U `unit` type to cube. - * @details E.g. `cubed` will represent meters^3. - */ - template - using cubed = typename units::detail::cubed_impl::type; - - /** @cond */ // DOXYGEN IGNORE - namespace detail - { - //---------------------------------- - // RATIO_SQRT IMPLEMENTATION - //---------------------------------- - - using Zero = std::ratio<0>; - using One = std::ratio<1>; - template using Square = std::ratio_multiply; - - // Find the largest std::integer N such that Predicate::value is true. - template