1*4d6fc14bSjoerg// -*- C++ -*- 2*4d6fc14bSjoerg//===---------------------------- ratio -----------------------------------===// 3*4d6fc14bSjoerg// 4*4d6fc14bSjoerg// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5*4d6fc14bSjoerg// See https://llvm.org/LICENSE.txt for license information. 6*4d6fc14bSjoerg// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7*4d6fc14bSjoerg// 8*4d6fc14bSjoerg//===----------------------------------------------------------------------===// 9*4d6fc14bSjoerg 10*4d6fc14bSjoerg#ifndef _LIBCPP_RATIO 11*4d6fc14bSjoerg#define _LIBCPP_RATIO 12*4d6fc14bSjoerg 13*4d6fc14bSjoerg/* 14*4d6fc14bSjoerg ratio synopsis 15*4d6fc14bSjoerg 16*4d6fc14bSjoergnamespace std 17*4d6fc14bSjoerg{ 18*4d6fc14bSjoerg 19*4d6fc14bSjoergtemplate <intmax_t N, intmax_t D = 1> 20*4d6fc14bSjoergclass ratio 21*4d6fc14bSjoerg{ 22*4d6fc14bSjoergpublic: 23*4d6fc14bSjoerg static constexpr intmax_t num; 24*4d6fc14bSjoerg static constexpr intmax_t den; 25*4d6fc14bSjoerg typedef ratio<num, den> type; 26*4d6fc14bSjoerg}; 27*4d6fc14bSjoerg 28*4d6fc14bSjoerg// ratio arithmetic 29*4d6fc14bSjoergtemplate <class R1, class R2> using ratio_add = ...; 30*4d6fc14bSjoergtemplate <class R1, class R2> using ratio_subtract = ...; 31*4d6fc14bSjoergtemplate <class R1, class R2> using ratio_multiply = ...; 32*4d6fc14bSjoergtemplate <class R1, class R2> using ratio_divide = ...; 33*4d6fc14bSjoerg 34*4d6fc14bSjoerg// ratio comparison 35*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_equal; 36*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_not_equal; 37*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_less; 38*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_less_equal; 39*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_greater; 40*4d6fc14bSjoergtemplate <class R1, class R2> struct ratio_greater_equal; 41*4d6fc14bSjoerg 42*4d6fc14bSjoerg// convenience SI typedefs 43*4d6fc14bSjoergtypedef ratio<1, 1000000000000000000000000> yocto; // not supported 44*4d6fc14bSjoergtypedef ratio<1, 1000000000000000000000> zepto; // not supported 45*4d6fc14bSjoergtypedef ratio<1, 1000000000000000000> atto; 46*4d6fc14bSjoergtypedef ratio<1, 1000000000000000> femto; 47*4d6fc14bSjoergtypedef ratio<1, 1000000000000> pico; 48*4d6fc14bSjoergtypedef ratio<1, 1000000000> nano; 49*4d6fc14bSjoergtypedef ratio<1, 1000000> micro; 50*4d6fc14bSjoergtypedef ratio<1, 1000> milli; 51*4d6fc14bSjoergtypedef ratio<1, 100> centi; 52*4d6fc14bSjoergtypedef ratio<1, 10> deci; 53*4d6fc14bSjoergtypedef ratio< 10, 1> deca; 54*4d6fc14bSjoergtypedef ratio< 100, 1> hecto; 55*4d6fc14bSjoergtypedef ratio< 1000, 1> kilo; 56*4d6fc14bSjoergtypedef ratio< 1000000, 1> mega; 57*4d6fc14bSjoergtypedef ratio< 1000000000, 1> giga; 58*4d6fc14bSjoergtypedef ratio< 1000000000000, 1> tera; 59*4d6fc14bSjoergtypedef ratio< 1000000000000000, 1> peta; 60*4d6fc14bSjoergtypedef ratio< 1000000000000000000, 1> exa; 61*4d6fc14bSjoergtypedef ratio< 1000000000000000000000, 1> zetta; // not supported 62*4d6fc14bSjoergtypedef ratio<1000000000000000000000000, 1> yotta; // not supported 63*4d6fc14bSjoerg 64*4d6fc14bSjoerg // 20.11.5, ratio comparison 65*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_equal_v 66*4d6fc14bSjoerg = ratio_equal<R1, R2>::value; // C++17 67*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_not_equal_v 68*4d6fc14bSjoerg = ratio_not_equal<R1, R2>::value; // C++17 69*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_less_v 70*4d6fc14bSjoerg = ratio_less<R1, R2>::value; // C++17 71*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_less_equal_v 72*4d6fc14bSjoerg = ratio_less_equal<R1, R2>::value; // C++17 73*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_greater_v 74*4d6fc14bSjoerg = ratio_greater<R1, R2>::value; // C++17 75*4d6fc14bSjoerg template <class R1, class R2> inline constexpr bool ratio_greater_equal_v 76*4d6fc14bSjoerg = ratio_greater_equal<R1, R2>::value; // C++17 77*4d6fc14bSjoerg} 78*4d6fc14bSjoerg*/ 79*4d6fc14bSjoerg 80*4d6fc14bSjoerg#include <__config> 81*4d6fc14bSjoerg#include <cstdint> 82*4d6fc14bSjoerg#include <climits> 83*4d6fc14bSjoerg#include <type_traits> 84*4d6fc14bSjoerg 85*4d6fc14bSjoerg#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 86*4d6fc14bSjoerg#pragma GCC system_header 87*4d6fc14bSjoerg#endif 88*4d6fc14bSjoerg 89*4d6fc14bSjoerg_LIBCPP_PUSH_MACROS 90*4d6fc14bSjoerg#include <__undef_macros> 91*4d6fc14bSjoerg 92*4d6fc14bSjoerg 93*4d6fc14bSjoerg_LIBCPP_BEGIN_NAMESPACE_STD 94*4d6fc14bSjoerg 95*4d6fc14bSjoerg// __static_gcd 96*4d6fc14bSjoerg 97*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 98*4d6fc14bSjoergstruct __static_gcd 99*4d6fc14bSjoerg{ 100*4d6fc14bSjoerg static const intmax_t value = __static_gcd<_Yp, _Xp % _Yp>::value; 101*4d6fc14bSjoerg}; 102*4d6fc14bSjoerg 103*4d6fc14bSjoergtemplate <intmax_t _Xp> 104*4d6fc14bSjoergstruct __static_gcd<_Xp, 0> 105*4d6fc14bSjoerg{ 106*4d6fc14bSjoerg static const intmax_t value = _Xp; 107*4d6fc14bSjoerg}; 108*4d6fc14bSjoerg 109*4d6fc14bSjoergtemplate <> 110*4d6fc14bSjoergstruct __static_gcd<0, 0> 111*4d6fc14bSjoerg{ 112*4d6fc14bSjoerg static const intmax_t value = 1; 113*4d6fc14bSjoerg}; 114*4d6fc14bSjoerg 115*4d6fc14bSjoerg// __static_lcm 116*4d6fc14bSjoerg 117*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 118*4d6fc14bSjoergstruct __static_lcm 119*4d6fc14bSjoerg{ 120*4d6fc14bSjoerg static const intmax_t value = _Xp / __static_gcd<_Xp, _Yp>::value * _Yp; 121*4d6fc14bSjoerg}; 122*4d6fc14bSjoerg 123*4d6fc14bSjoergtemplate <intmax_t _Xp> 124*4d6fc14bSjoergstruct __static_abs 125*4d6fc14bSjoerg{ 126*4d6fc14bSjoerg static const intmax_t value = _Xp < 0 ? -_Xp : _Xp; 127*4d6fc14bSjoerg}; 128*4d6fc14bSjoerg 129*4d6fc14bSjoergtemplate <intmax_t _Xp> 130*4d6fc14bSjoergstruct __static_sign 131*4d6fc14bSjoerg{ 132*4d6fc14bSjoerg static const intmax_t value = _Xp == 0 ? 0 : (_Xp < 0 ? -1 : 1); 133*4d6fc14bSjoerg}; 134*4d6fc14bSjoerg 135*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp, intmax_t = __static_sign<_Yp>::value> 136*4d6fc14bSjoergclass __ll_add; 137*4d6fc14bSjoerg 138*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 139*4d6fc14bSjoergclass __ll_add<_Xp, _Yp, 1> 140*4d6fc14bSjoerg{ 141*4d6fc14bSjoerg static const intmax_t min = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)) + 1; 142*4d6fc14bSjoerg static const intmax_t max = -min; 143*4d6fc14bSjoerg 144*4d6fc14bSjoerg static_assert(_Xp <= max - _Yp, "overflow in __ll_add"); 145*4d6fc14bSjoergpublic: 146*4d6fc14bSjoerg static const intmax_t value = _Xp + _Yp; 147*4d6fc14bSjoerg}; 148*4d6fc14bSjoerg 149*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 150*4d6fc14bSjoergclass __ll_add<_Xp, _Yp, 0> 151*4d6fc14bSjoerg{ 152*4d6fc14bSjoergpublic: 153*4d6fc14bSjoerg static const intmax_t value = _Xp; 154*4d6fc14bSjoerg}; 155*4d6fc14bSjoerg 156*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 157*4d6fc14bSjoergclass __ll_add<_Xp, _Yp, -1> 158*4d6fc14bSjoerg{ 159*4d6fc14bSjoerg static const intmax_t min = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)) + 1; 160*4d6fc14bSjoerg static const intmax_t max = -min; 161*4d6fc14bSjoerg 162*4d6fc14bSjoerg static_assert(min - _Yp <= _Xp, "overflow in __ll_add"); 163*4d6fc14bSjoergpublic: 164*4d6fc14bSjoerg static const intmax_t value = _Xp + _Yp; 165*4d6fc14bSjoerg}; 166*4d6fc14bSjoerg 167*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp, intmax_t = __static_sign<_Yp>::value> 168*4d6fc14bSjoergclass __ll_sub; 169*4d6fc14bSjoerg 170*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 171*4d6fc14bSjoergclass __ll_sub<_Xp, _Yp, 1> 172*4d6fc14bSjoerg{ 173*4d6fc14bSjoerg static const intmax_t min = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)) + 1; 174*4d6fc14bSjoerg static const intmax_t max = -min; 175*4d6fc14bSjoerg 176*4d6fc14bSjoerg static_assert(min + _Yp <= _Xp, "overflow in __ll_sub"); 177*4d6fc14bSjoergpublic: 178*4d6fc14bSjoerg static const intmax_t value = _Xp - _Yp; 179*4d6fc14bSjoerg}; 180*4d6fc14bSjoerg 181*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 182*4d6fc14bSjoergclass __ll_sub<_Xp, _Yp, 0> 183*4d6fc14bSjoerg{ 184*4d6fc14bSjoergpublic: 185*4d6fc14bSjoerg static const intmax_t value = _Xp; 186*4d6fc14bSjoerg}; 187*4d6fc14bSjoerg 188*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 189*4d6fc14bSjoergclass __ll_sub<_Xp, _Yp, -1> 190*4d6fc14bSjoerg{ 191*4d6fc14bSjoerg static const intmax_t min = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)) + 1; 192*4d6fc14bSjoerg static const intmax_t max = -min; 193*4d6fc14bSjoerg 194*4d6fc14bSjoerg static_assert(_Xp <= max + _Yp, "overflow in __ll_sub"); 195*4d6fc14bSjoergpublic: 196*4d6fc14bSjoerg static const intmax_t value = _Xp - _Yp; 197*4d6fc14bSjoerg}; 198*4d6fc14bSjoerg 199*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 200*4d6fc14bSjoergclass __ll_mul 201*4d6fc14bSjoerg{ 202*4d6fc14bSjoerg static const intmax_t nan = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)); 203*4d6fc14bSjoerg static const intmax_t min = nan + 1; 204*4d6fc14bSjoerg static const intmax_t max = -min; 205*4d6fc14bSjoerg static const intmax_t __a_x = __static_abs<_Xp>::value; 206*4d6fc14bSjoerg static const intmax_t __a_y = __static_abs<_Yp>::value; 207*4d6fc14bSjoerg 208*4d6fc14bSjoerg static_assert(_Xp != nan && _Yp != nan && __a_x <= max / __a_y, "overflow in __ll_mul"); 209*4d6fc14bSjoergpublic: 210*4d6fc14bSjoerg static const intmax_t value = _Xp * _Yp; 211*4d6fc14bSjoerg}; 212*4d6fc14bSjoerg 213*4d6fc14bSjoergtemplate <intmax_t _Yp> 214*4d6fc14bSjoergclass __ll_mul<0, _Yp> 215*4d6fc14bSjoerg{ 216*4d6fc14bSjoergpublic: 217*4d6fc14bSjoerg static const intmax_t value = 0; 218*4d6fc14bSjoerg}; 219*4d6fc14bSjoerg 220*4d6fc14bSjoergtemplate <intmax_t _Xp> 221*4d6fc14bSjoergclass __ll_mul<_Xp, 0> 222*4d6fc14bSjoerg{ 223*4d6fc14bSjoergpublic: 224*4d6fc14bSjoerg static const intmax_t value = 0; 225*4d6fc14bSjoerg}; 226*4d6fc14bSjoerg 227*4d6fc14bSjoergtemplate <> 228*4d6fc14bSjoergclass __ll_mul<0, 0> 229*4d6fc14bSjoerg{ 230*4d6fc14bSjoergpublic: 231*4d6fc14bSjoerg static const intmax_t value = 0; 232*4d6fc14bSjoerg}; 233*4d6fc14bSjoerg 234*4d6fc14bSjoerg// Not actually used but left here in case needed in future maintenance 235*4d6fc14bSjoergtemplate <intmax_t _Xp, intmax_t _Yp> 236*4d6fc14bSjoergclass __ll_div 237*4d6fc14bSjoerg{ 238*4d6fc14bSjoerg static const intmax_t nan = (1LL << (sizeof(intmax_t) * CHAR_BIT - 1)); 239*4d6fc14bSjoerg static const intmax_t min = nan + 1; 240*4d6fc14bSjoerg static const intmax_t max = -min; 241*4d6fc14bSjoerg 242*4d6fc14bSjoerg static_assert(_Xp != nan && _Yp != nan && _Yp != 0, "overflow in __ll_div"); 243*4d6fc14bSjoergpublic: 244*4d6fc14bSjoerg static const intmax_t value = _Xp / _Yp; 245*4d6fc14bSjoerg}; 246*4d6fc14bSjoerg 247*4d6fc14bSjoergtemplate <intmax_t _Num, intmax_t _Den = 1> 248*4d6fc14bSjoergclass _LIBCPP_TEMPLATE_VIS ratio 249*4d6fc14bSjoerg{ 250*4d6fc14bSjoerg static_assert(__static_abs<_Num>::value >= 0, "ratio numerator is out of range"); 251*4d6fc14bSjoerg static_assert(_Den != 0, "ratio divide by 0"); 252*4d6fc14bSjoerg static_assert(__static_abs<_Den>::value > 0, "ratio denominator is out of range"); 253*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t __na = __static_abs<_Num>::value; 254*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t __da = __static_abs<_Den>::value; 255*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t __s = __static_sign<_Num>::value * __static_sign<_Den>::value; 256*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t __gcd = __static_gcd<__na, __da>::value; 257*4d6fc14bSjoergpublic: 258*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t num = __s * __na / __gcd; 259*4d6fc14bSjoerg static _LIBCPP_CONSTEXPR const intmax_t den = __da / __gcd; 260*4d6fc14bSjoerg 261*4d6fc14bSjoerg typedef ratio<num, den> type; 262*4d6fc14bSjoerg}; 263*4d6fc14bSjoerg 264*4d6fc14bSjoergtemplate <intmax_t _Num, intmax_t _Den> 265*4d6fc14bSjoerg_LIBCPP_CONSTEXPR const intmax_t ratio<_Num, _Den>::num; 266*4d6fc14bSjoerg 267*4d6fc14bSjoergtemplate <intmax_t _Num, intmax_t _Den> 268*4d6fc14bSjoerg_LIBCPP_CONSTEXPR const intmax_t ratio<_Num, _Den>::den; 269*4d6fc14bSjoerg 270*4d6fc14bSjoergtemplate <class _Tp> struct __is_ratio : false_type {}; 271*4d6fc14bSjoergtemplate <intmax_t _Num, intmax_t _Den> struct __is_ratio<ratio<_Num, _Den> > : true_type {}; 272*4d6fc14bSjoerg 273*4d6fc14bSjoergtypedef ratio<1LL, 1000000000000000000LL> atto; 274*4d6fc14bSjoergtypedef ratio<1LL, 1000000000000000LL> femto; 275*4d6fc14bSjoergtypedef ratio<1LL, 1000000000000LL> pico; 276*4d6fc14bSjoergtypedef ratio<1LL, 1000000000LL> nano; 277*4d6fc14bSjoergtypedef ratio<1LL, 1000000LL> micro; 278*4d6fc14bSjoergtypedef ratio<1LL, 1000LL> milli; 279*4d6fc14bSjoergtypedef ratio<1LL, 100LL> centi; 280*4d6fc14bSjoergtypedef ratio<1LL, 10LL> deci; 281*4d6fc14bSjoergtypedef ratio< 10LL, 1LL> deca; 282*4d6fc14bSjoergtypedef ratio< 100LL, 1LL> hecto; 283*4d6fc14bSjoergtypedef ratio< 1000LL, 1LL> kilo; 284*4d6fc14bSjoergtypedef ratio< 1000000LL, 1LL> mega; 285*4d6fc14bSjoergtypedef ratio< 1000000000LL, 1LL> giga; 286*4d6fc14bSjoergtypedef ratio< 1000000000000LL, 1LL> tera; 287*4d6fc14bSjoergtypedef ratio< 1000000000000000LL, 1LL> peta; 288*4d6fc14bSjoergtypedef ratio<1000000000000000000LL, 1LL> exa; 289*4d6fc14bSjoerg 290*4d6fc14bSjoergtemplate <class _R1, class _R2> 291*4d6fc14bSjoergstruct __ratio_multiply 292*4d6fc14bSjoerg{ 293*4d6fc14bSjoergprivate: 294*4d6fc14bSjoerg static const intmax_t __gcd_n1_d2 = __static_gcd<_R1::num, _R2::den>::value; 295*4d6fc14bSjoerg static const intmax_t __gcd_d1_n2 = __static_gcd<_R1::den, _R2::num>::value; 296*4d6fc14bSjoergpublic: 297*4d6fc14bSjoerg typedef typename ratio 298*4d6fc14bSjoerg < 299*4d6fc14bSjoerg __ll_mul<_R1::num / __gcd_n1_d2, _R2::num / __gcd_d1_n2>::value, 300*4d6fc14bSjoerg __ll_mul<_R2::den / __gcd_n1_d2, _R1::den / __gcd_d1_n2>::value 301*4d6fc14bSjoerg >::type type; 302*4d6fc14bSjoerg}; 303*4d6fc14bSjoerg 304*4d6fc14bSjoerg#ifndef _LIBCPP_CXX03_LANG 305*4d6fc14bSjoerg 306*4d6fc14bSjoergtemplate <class _R1, class _R2> using ratio_multiply 307*4d6fc14bSjoerg = typename __ratio_multiply<_R1, _R2>::type; 308*4d6fc14bSjoerg 309*4d6fc14bSjoerg#else // _LIBCPP_CXX03_LANG 310*4d6fc14bSjoerg 311*4d6fc14bSjoergtemplate <class _R1, class _R2> 312*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_multiply 313*4d6fc14bSjoerg : public __ratio_multiply<_R1, _R2>::type {}; 314*4d6fc14bSjoerg 315*4d6fc14bSjoerg#endif // _LIBCPP_CXX03_LANG 316*4d6fc14bSjoerg 317*4d6fc14bSjoergtemplate <class _R1, class _R2> 318*4d6fc14bSjoergstruct __ratio_divide 319*4d6fc14bSjoerg{ 320*4d6fc14bSjoergprivate: 321*4d6fc14bSjoerg static const intmax_t __gcd_n1_n2 = __static_gcd<_R1::num, _R2::num>::value; 322*4d6fc14bSjoerg static const intmax_t __gcd_d1_d2 = __static_gcd<_R1::den, _R2::den>::value; 323*4d6fc14bSjoergpublic: 324*4d6fc14bSjoerg typedef typename ratio 325*4d6fc14bSjoerg < 326*4d6fc14bSjoerg __ll_mul<_R1::num / __gcd_n1_n2, _R2::den / __gcd_d1_d2>::value, 327*4d6fc14bSjoerg __ll_mul<_R2::num / __gcd_n1_n2, _R1::den / __gcd_d1_d2>::value 328*4d6fc14bSjoerg >::type type; 329*4d6fc14bSjoerg}; 330*4d6fc14bSjoerg 331*4d6fc14bSjoerg#ifndef _LIBCPP_CXX03_LANG 332*4d6fc14bSjoerg 333*4d6fc14bSjoergtemplate <class _R1, class _R2> using ratio_divide 334*4d6fc14bSjoerg = typename __ratio_divide<_R1, _R2>::type; 335*4d6fc14bSjoerg 336*4d6fc14bSjoerg#else // _LIBCPP_CXX03_LANG 337*4d6fc14bSjoerg 338*4d6fc14bSjoergtemplate <class _R1, class _R2> 339*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_divide 340*4d6fc14bSjoerg : public __ratio_divide<_R1, _R2>::type {}; 341*4d6fc14bSjoerg 342*4d6fc14bSjoerg#endif // _LIBCPP_CXX03_LANG 343*4d6fc14bSjoerg 344*4d6fc14bSjoergtemplate <class _R1, class _R2> 345*4d6fc14bSjoergstruct __ratio_add 346*4d6fc14bSjoerg{ 347*4d6fc14bSjoergprivate: 348*4d6fc14bSjoerg static const intmax_t __gcd_n1_n2 = __static_gcd<_R1::num, _R2::num>::value; 349*4d6fc14bSjoerg static const intmax_t __gcd_d1_d2 = __static_gcd<_R1::den, _R2::den>::value; 350*4d6fc14bSjoergpublic: 351*4d6fc14bSjoerg typedef typename ratio_multiply 352*4d6fc14bSjoerg < 353*4d6fc14bSjoerg ratio<__gcd_n1_n2, _R1::den / __gcd_d1_d2>, 354*4d6fc14bSjoerg ratio 355*4d6fc14bSjoerg < 356*4d6fc14bSjoerg __ll_add 357*4d6fc14bSjoerg < 358*4d6fc14bSjoerg __ll_mul<_R1::num / __gcd_n1_n2, _R2::den / __gcd_d1_d2>::value, 359*4d6fc14bSjoerg __ll_mul<_R2::num / __gcd_n1_n2, _R1::den / __gcd_d1_d2>::value 360*4d6fc14bSjoerg >::value, 361*4d6fc14bSjoerg _R2::den 362*4d6fc14bSjoerg > 363*4d6fc14bSjoerg >::type type; 364*4d6fc14bSjoerg}; 365*4d6fc14bSjoerg 366*4d6fc14bSjoerg#ifndef _LIBCPP_CXX03_LANG 367*4d6fc14bSjoerg 368*4d6fc14bSjoergtemplate <class _R1, class _R2> using ratio_add 369*4d6fc14bSjoerg = typename __ratio_add<_R1, _R2>::type; 370*4d6fc14bSjoerg 371*4d6fc14bSjoerg#else // _LIBCPP_CXX03_LANG 372*4d6fc14bSjoerg 373*4d6fc14bSjoergtemplate <class _R1, class _R2> 374*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_add 375*4d6fc14bSjoerg : public __ratio_add<_R1, _R2>::type {}; 376*4d6fc14bSjoerg 377*4d6fc14bSjoerg#endif // _LIBCPP_CXX03_LANG 378*4d6fc14bSjoerg 379*4d6fc14bSjoergtemplate <class _R1, class _R2> 380*4d6fc14bSjoergstruct __ratio_subtract 381*4d6fc14bSjoerg{ 382*4d6fc14bSjoergprivate: 383*4d6fc14bSjoerg static const intmax_t __gcd_n1_n2 = __static_gcd<_R1::num, _R2::num>::value; 384*4d6fc14bSjoerg static const intmax_t __gcd_d1_d2 = __static_gcd<_R1::den, _R2::den>::value; 385*4d6fc14bSjoergpublic: 386*4d6fc14bSjoerg typedef typename ratio_multiply 387*4d6fc14bSjoerg < 388*4d6fc14bSjoerg ratio<__gcd_n1_n2, _R1::den / __gcd_d1_d2>, 389*4d6fc14bSjoerg ratio 390*4d6fc14bSjoerg < 391*4d6fc14bSjoerg __ll_sub 392*4d6fc14bSjoerg < 393*4d6fc14bSjoerg __ll_mul<_R1::num / __gcd_n1_n2, _R2::den / __gcd_d1_d2>::value, 394*4d6fc14bSjoerg __ll_mul<_R2::num / __gcd_n1_n2, _R1::den / __gcd_d1_d2>::value 395*4d6fc14bSjoerg >::value, 396*4d6fc14bSjoerg _R2::den 397*4d6fc14bSjoerg > 398*4d6fc14bSjoerg >::type type; 399*4d6fc14bSjoerg}; 400*4d6fc14bSjoerg 401*4d6fc14bSjoerg#ifndef _LIBCPP_CXX03_LANG 402*4d6fc14bSjoerg 403*4d6fc14bSjoergtemplate <class _R1, class _R2> using ratio_subtract 404*4d6fc14bSjoerg = typename __ratio_subtract<_R1, _R2>::type; 405*4d6fc14bSjoerg 406*4d6fc14bSjoerg#else // _LIBCPP_CXX03_LANG 407*4d6fc14bSjoerg 408*4d6fc14bSjoergtemplate <class _R1, class _R2> 409*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_subtract 410*4d6fc14bSjoerg : public __ratio_subtract<_R1, _R2>::type {}; 411*4d6fc14bSjoerg 412*4d6fc14bSjoerg#endif // _LIBCPP_CXX03_LANG 413*4d6fc14bSjoerg 414*4d6fc14bSjoerg// ratio_equal 415*4d6fc14bSjoerg 416*4d6fc14bSjoergtemplate <class _R1, class _R2> 417*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_equal 418*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((_R1::num == _R2::num && _R1::den == _R2::den)) {}; 419*4d6fc14bSjoerg 420*4d6fc14bSjoergtemplate <class _R1, class _R2> 421*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_not_equal 422*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((!ratio_equal<_R1, _R2>::value)) {}; 423*4d6fc14bSjoerg 424*4d6fc14bSjoerg// ratio_less 425*4d6fc14bSjoerg 426*4d6fc14bSjoergtemplate <class _R1, class _R2, bool _Odd = false, 427*4d6fc14bSjoerg intmax_t _Q1 = _R1::num / _R1::den, intmax_t _M1 = _R1::num % _R1::den, 428*4d6fc14bSjoerg intmax_t _Q2 = _R2::num / _R2::den, intmax_t _M2 = _R2::num % _R2::den> 429*4d6fc14bSjoergstruct __ratio_less1 430*4d6fc14bSjoerg{ 431*4d6fc14bSjoerg static const bool value = _Odd ? _Q2 < _Q1 : _Q1 < _Q2; 432*4d6fc14bSjoerg}; 433*4d6fc14bSjoerg 434*4d6fc14bSjoergtemplate <class _R1, class _R2, bool _Odd, intmax_t _Qp> 435*4d6fc14bSjoergstruct __ratio_less1<_R1, _R2, _Odd, _Qp, 0, _Qp, 0> 436*4d6fc14bSjoerg{ 437*4d6fc14bSjoerg static const bool value = false; 438*4d6fc14bSjoerg}; 439*4d6fc14bSjoerg 440*4d6fc14bSjoergtemplate <class _R1, class _R2, bool _Odd, intmax_t _Qp, intmax_t _M2> 441*4d6fc14bSjoergstruct __ratio_less1<_R1, _R2, _Odd, _Qp, 0, _Qp, _M2> 442*4d6fc14bSjoerg{ 443*4d6fc14bSjoerg static const bool value = !_Odd; 444*4d6fc14bSjoerg}; 445*4d6fc14bSjoerg 446*4d6fc14bSjoergtemplate <class _R1, class _R2, bool _Odd, intmax_t _Qp, intmax_t _M1> 447*4d6fc14bSjoergstruct __ratio_less1<_R1, _R2, _Odd, _Qp, _M1, _Qp, 0> 448*4d6fc14bSjoerg{ 449*4d6fc14bSjoerg static const bool value = _Odd; 450*4d6fc14bSjoerg}; 451*4d6fc14bSjoerg 452*4d6fc14bSjoergtemplate <class _R1, class _R2, bool _Odd, intmax_t _Qp, intmax_t _M1, 453*4d6fc14bSjoerg intmax_t _M2> 454*4d6fc14bSjoergstruct __ratio_less1<_R1, _R2, _Odd, _Qp, _M1, _Qp, _M2> 455*4d6fc14bSjoerg{ 456*4d6fc14bSjoerg static const bool value = __ratio_less1<ratio<_R1::den, _M1>, 457*4d6fc14bSjoerg ratio<_R2::den, _M2>, !_Odd>::value; 458*4d6fc14bSjoerg}; 459*4d6fc14bSjoerg 460*4d6fc14bSjoergtemplate <class _R1, class _R2, intmax_t _S1 = __static_sign<_R1::num>::value, 461*4d6fc14bSjoerg intmax_t _S2 = __static_sign<_R2::num>::value> 462*4d6fc14bSjoergstruct __ratio_less 463*4d6fc14bSjoerg{ 464*4d6fc14bSjoerg static const bool value = _S1 < _S2; 465*4d6fc14bSjoerg}; 466*4d6fc14bSjoerg 467*4d6fc14bSjoergtemplate <class _R1, class _R2> 468*4d6fc14bSjoergstruct __ratio_less<_R1, _R2, 1LL, 1LL> 469*4d6fc14bSjoerg{ 470*4d6fc14bSjoerg static const bool value = __ratio_less1<_R1, _R2>::value; 471*4d6fc14bSjoerg}; 472*4d6fc14bSjoerg 473*4d6fc14bSjoergtemplate <class _R1, class _R2> 474*4d6fc14bSjoergstruct __ratio_less<_R1, _R2, -1LL, -1LL> 475*4d6fc14bSjoerg{ 476*4d6fc14bSjoerg static const bool value = __ratio_less1<ratio<-_R2::num, _R2::den>, ratio<-_R1::num, _R1::den> >::value; 477*4d6fc14bSjoerg}; 478*4d6fc14bSjoerg 479*4d6fc14bSjoergtemplate <class _R1, class _R2> 480*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_less 481*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((__ratio_less<_R1, _R2>::value)) {}; 482*4d6fc14bSjoerg 483*4d6fc14bSjoergtemplate <class _R1, class _R2> 484*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_less_equal 485*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((!ratio_less<_R2, _R1>::value)) {}; 486*4d6fc14bSjoerg 487*4d6fc14bSjoergtemplate <class _R1, class _R2> 488*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_greater 489*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((ratio_less<_R2, _R1>::value)) {}; 490*4d6fc14bSjoerg 491*4d6fc14bSjoergtemplate <class _R1, class _R2> 492*4d6fc14bSjoergstruct _LIBCPP_TEMPLATE_VIS ratio_greater_equal 493*4d6fc14bSjoerg : public _LIBCPP_BOOL_CONSTANT((!ratio_less<_R1, _R2>::value)) {}; 494*4d6fc14bSjoerg 495*4d6fc14bSjoergtemplate <class _R1, class _R2> 496*4d6fc14bSjoergstruct __ratio_gcd 497*4d6fc14bSjoerg{ 498*4d6fc14bSjoerg typedef ratio<__static_gcd<_R1::num, _R2::num>::value, 499*4d6fc14bSjoerg __static_lcm<_R1::den, _R2::den>::value> type; 500*4d6fc14bSjoerg}; 501*4d6fc14bSjoerg 502*4d6fc14bSjoerg#if _LIBCPP_STD_VER > 14 && !defined(_LIBCPP_HAS_NO_VARIABLE_TEMPLATES) 503*4d6fc14bSjoergtemplate <class _R1, class _R2> 504*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_equal_v 505*4d6fc14bSjoerg = ratio_equal<_R1, _R2>::value; 506*4d6fc14bSjoerg 507*4d6fc14bSjoergtemplate <class _R1, class _R2> 508*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_not_equal_v 509*4d6fc14bSjoerg = ratio_not_equal<_R1, _R2>::value; 510*4d6fc14bSjoerg 511*4d6fc14bSjoergtemplate <class _R1, class _R2> 512*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_less_v 513*4d6fc14bSjoerg = ratio_less<_R1, _R2>::value; 514*4d6fc14bSjoerg 515*4d6fc14bSjoergtemplate <class _R1, class _R2> 516*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_less_equal_v 517*4d6fc14bSjoerg = ratio_less_equal<_R1, _R2>::value; 518*4d6fc14bSjoerg 519*4d6fc14bSjoergtemplate <class _R1, class _R2> 520*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_greater_v 521*4d6fc14bSjoerg = ratio_greater<_R1, _R2>::value; 522*4d6fc14bSjoerg 523*4d6fc14bSjoergtemplate <class _R1, class _R2> 524*4d6fc14bSjoerg_LIBCPP_INLINE_VAR _LIBCPP_CONSTEXPR bool ratio_greater_equal_v 525*4d6fc14bSjoerg = ratio_greater_equal<_R1, _R2>::value; 526*4d6fc14bSjoerg#endif 527*4d6fc14bSjoerg 528*4d6fc14bSjoerg_LIBCPP_END_NAMESPACE_STD 529*4d6fc14bSjoerg 530*4d6fc14bSjoerg_LIBCPP_POP_MACROS 531*4d6fc14bSjoerg 532*4d6fc14bSjoerg#endif // _LIBCPP_RATIO 533