lmi-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[lmi-commits] [lmi] master 3718824 2/6: Improve interest-conversion exam


From: Greg Chicares
Subject: [lmi-commits] [lmi] master 3718824 2/6: Improve interest-conversion example
Date: Sun, 30 Apr 2017 11:49:36 -0400 (EDT)

branch: master
commit 37188242db519121cd9feb2755f0ff3ff6017cf2
Author: Gregory W. Chicares <address@hidden>
Commit: Gregory W. Chicares <address@hidden>

    Improve interest-conversion example
    
    The replaced example used a more obscure calculation and actually
    produced only two distinct values for four methods.
---
 math_functors_test.cpp | 40 +++++++++++++++++++++++++++++++++-------
 1 file changed, 33 insertions(+), 7 deletions(-)

diff --git a/math_functors_test.cpp b/math_functors_test.cpp
index 2e2ebb3..82efe82 100644
--- a/math_functors_test.cpp
+++ b/math_functors_test.cpp
@@ -125,6 +125,30 @@ struct coi_rate_from_q_naive
             }
         }
 };
+
+template<typename T, int n>
+struct i_upper_n_over_n_from_i_naive
+{
+    static_assert(std::is_floating_point<T>::value, "");
+    T operator()(T const& i) const
+        {
+        return T(-1) + std::pow((T(1) + i), T(1) / n);
+        }
+};
+
+// This implementation uses std::expm1() and std::log1p() for type T,
+// rather than the long double functions used in production.
+
+template<typename T, int n>
+struct i_upper_n_over_n_from_i_T
+{
+    static_assert(std::is_floating_point<T>::value, "");
+    T operator()(T const& i) const
+        {
+        static T const reciprocal_n = T(1) / n;
+        return std::expm1(std::log1p(i) * reciprocal_n);
+        }
+};
 } // Unnamed namespace.
 
 /// This function isn't a unit test per se. Its purpose is to show
@@ -140,29 +164,31 @@ struct coi_rate_from_q_naive
 void sample_results()
 {
     fenv_initialize();
+    std::cout.setf(std::ios_base::fixed, std::ios_base::floatfield);
+    std::cout.precision(25);
     std::cout
-        << "\n  annual rate corresponding to a 0.004 daily spread"
+        << "\n  daily rate corresponding to 1% annual interest"
         << ", by various methods\n"
+        << "    method in production\n      "
+        << i_upper_n_over_n_from_i      <long double,365>()(0.01) << '\n'
         ;
 #if defined LMI_X87
     fenv_precision(fe_ldblprec);
     std::cout
-        << std::setprecision(20)
         << "    long double precision, std::expm1 and std::log1p\n      "
-        << net_i_from_gross<double,365>()(0.0, 0.004, 0.0) << '\n'
+        << i_upper_n_over_n_from_i_T    <long double,365>()(0.01) << '\n'
         << "    long double precision, std::pow\n      "
-        << net_i_from_gross_naive<double,365>()(0.0, 0.004, 0.0) << '\n'
+        << i_upper_n_over_n_from_i_naive<long double,365>()(0.01) << '\n'
         ;
 
     fenv_initialize();
     fenv_precision(fe_dblprec);
 #endif // defined LMI_X87
     std::cout
-        << std::setprecision(20)
         << "    double precision, std::expm1 and std::log1p\n      "
-        << net_i_from_gross<double,365>      ()(0.0, 0.004, 0.0) << '\n'
+        << i_upper_n_over_n_from_i_T    <double,365>()(0.01) << '\n'
         << "    double precision, std::pow\n      "
-        << net_i_from_gross_naive<double,365>()(0.0, 0.004, 0.0) << '\n'
+        << i_upper_n_over_n_from_i_naive<double,365>()(0.01) << '\n'
         ;
 
     fenv_initialize();



reply via email to

[Prev in Thread] Current Thread [Next in Thread]