[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[lmi-commits] [lmi] valyuta/004 50ed405 3/9: Prefer explicit to implicit
From: |
Greg Chicares |
Subject: |
[lmi-commits] [lmi] valyuta/004 50ed405 3/9: Prefer explicit to implicit currency rounding |
Date: |
Tue, 29 Dec 2020 14:46:01 -0500 (EST) |
branch: valyuta/004
commit 50ed4050acf3ded17fb862f559591d81d22b7de0
Author: Gregory W. Chicares <gchicares@sbcglobal.net>
Commit: Gregory W. Chicares <gchicares@sbcglobal.net>
Prefer explicit to implicit currency rounding
Incidentally, the commentary added to 'loads_impl.hpp' explains why
'TgtPremMonthlyPolFee' is rounded with a gross-premium rule (as seems
natural), but class Loads uses a different rule for other policy fees.
---
accountvalue.cpp | 13 +++++++------
basicvalues.cpp | 6 +++---
ihs_acctval.cpp | 11 ++++++-----
ihs_basicval.cpp | 16 ++++++++--------
loads_impl.hpp | 6 +++++-
5 files changed, 29 insertions(+), 23 deletions(-)
diff --git a/accountvalue.cpp b/accountvalue.cpp
index 69dd868..e848495 100644
--- a/accountvalue.cpp
+++ b/accountvalue.cpp
@@ -128,7 +128,8 @@ AccountValue::AccountValue(Input const& input)
currency AccountValue::base_specamt(int year) const
{
- return currency(InvariantValues().SpecAmt[year]);
+ // CURRENCY !! Cents in ledger will make rounding unnecessary.
+ return round_specamt().c(InvariantValues().SpecAmt[year]);
}
//============================================================================
@@ -222,7 +223,7 @@ void AccountValue::RunOneCell(mcenum_run_basis TheBasis)
InforceYear = yare_input_.InforceYear;
InforceMonth = yare_input_.InforceMonth;
- InforceAVGenAcct = currency(yare_input_.InforceGeneralAccountValue);
+ InforceAVGenAcct =
round_minutiae().c(yare_input_.InforceGeneralAccountValue);
ItLapsed = false;
LapseMonth = 0;
@@ -282,7 +283,7 @@ void AccountValue::DoYear
pmt = stored_pmts[Year];
YearsPremLoadTgt = Loads_->target_premium_load(GenBasis_)[Year];
- YearsMonthlyPolicyFee =
currency(Loads_->monthly_policy_fee(GenBasis_)[Year]);
+ YearsMonthlyPolicyFee = Loads_->monthly_policy_fee (GenBasis_)[Year];
ActualSpecAmt = base_specamt(Year);
// These variables are set for each pass independently.
@@ -795,7 +796,7 @@ void AccountValue::TxSetRiderDed()
WpCharge = C0;
if(haswp)
{
- WpCharge = currency
+ WpCharge = round_rider_charges().c
(
YearsWpRate
* (CoiCharge + YearsMonthlyPolicyFee + AdbCharge)
@@ -805,7 +806,7 @@ void AccountValue::TxSetRiderDed()
AdbCharge = C0;
if(hasadb)
{
- AdbCharge = currency(YearsAdbRate * std::min(500000.0,
ActualSpecAmt.d()));
+ AdbCharge = round_rider_charges().c(YearsAdbRate * std::min(500000.0,
ActualSpecAmt.d()));
}
}
@@ -944,7 +945,7 @@ void AccountValue::TxTakeWD()
}
// Deduct withdrawal fee.
- wd -= std::min(WDFee, currency(wd * WDFeeRate));
+ wd -= std::min(WDFee, round_withdrawal().c(wd * WDFeeRate));
// IHS !! This treats input WD as gross; it probably should be net. But
compare lmi.
InvariantValues().NetWD[Year] = wd.d();
diff --git a/basicvalues.cpp b/basicvalues.cpp
index e83093b..da619ae 100644
--- a/basicvalues.cpp
+++ b/basicvalues.cpp
@@ -123,9 +123,9 @@ void BasicValues::Init()
// database().query_into(DB_MinWd , MinWD );
// database().query_into(DB_WdFee , WDFee );
// database().query_into(DB_WdFeeRate , WDFeeRate );
- MinSpecAmt = currency(database().query<int>(DB_MinSpecAmt));
- MinWD = currency(database().query<int>(DB_MinWd ));
- WDFee = currency(database().query<int>(DB_WdFee ));
+ MinSpecAmt = round_specamt ().c(database().query<int>(DB_MinSpecAmt));
+ MinWD = round_withdrawal().c(database().query<int>(DB_MinWd ));
+ WDFee = round_withdrawal().c(database().query<int>(DB_WdFee ));
// WDFeeRate = database().query<int>(DB_WdFeeRate ); // no, this line looks
wrong
database().query_into(DB_WdFeeRate , WDFeeRate );
diff --git a/ihs_acctval.cpp b/ihs_acctval.cpp
index b0d64f0..fdbf5aa 100644
--- a/ihs_acctval.cpp
+++ b/ihs_acctval.cpp
@@ -143,14 +143,16 @@ AccountValue::AccountValue(Input const& input)
currency AccountValue::base_specamt(int year) const
{
- return currency(InvariantValues().SpecAmt[year]);
+ // CURRENCY !! Cents in ledger will make rounding unnecessary.
+ return round_specamt().c(InvariantValues().SpecAmt[year]);
}
/// Specified amount of term rider.
currency AccountValue::term_specamt(int year) const
{
- return currency(InvariantValues().TermSpecAmt[year]);
+ // CURRENCY !! Cents in ledger will make rounding unnecessary.
+ return round_specamt().c(InvariantValues().TermSpecAmt[year]);
}
/// Specified amount for 7702 (not 7702A).
@@ -1372,9 +1374,8 @@ void AccountValue::SetAnnualInvariants()
{
YearsCorridorFactor = GetCorridorFactor()[Year];
YearsDBOpt = DeathBfts_->dbopt()[Year];
- // policy fee should be rounded in loads class
- YearsMonthlyPolicyFee =
currency(Loads_->monthly_policy_fee(GenBasis_)[Year]);
- YearsAnnualPolicyFee = currency(Loads_->annual_policy_fee
(GenBasis_)[Year]);
+ YearsMonthlyPolicyFee = Loads_->monthly_policy_fee(GenBasis_)[Year];
+ YearsAnnualPolicyFee = Loads_->annual_policy_fee (GenBasis_)[Year];
YearsGenAcctIntRate = InterestRates_->GenAcctNetRate
(GenBasis_
diff --git a/ihs_basicval.cpp b/ihs_basicval.cpp
index 0830e7f..5bc92ed 100644
--- a/ihs_basicval.cpp
+++ b/ihs_basicval.cpp
@@ -564,10 +564,10 @@ currency BasicValues::GetAnnualTgtPrem(int a_year,
currency a_specamt) const
void BasicValues::SetPermanentInvariants()
{
// maybe implement query_into<currency>
- MinIssSpecAmt = currency(database().query<int>(DB_MinIssSpecAmt
));
- MinIssBaseSpecAmt = currency(database().query<int>(DB_MinIssBaseSpecAmt
));
- MinRenlSpecAmt = currency(database().query<int>(DB_MinRenlSpecAmt
));
- MinRenlBaseSpecAmt =
currency(database().query<int>(DB_MinRenlBaseSpecAmt));
+ MinIssSpecAmt =
round_specamt().c(database().query<int>(DB_MinIssSpecAmt ));
+ MinIssBaseSpecAmt =
round_specamt().c(database().query<int>(DB_MinIssBaseSpecAmt ));
+ MinRenlSpecAmt =
round_specamt().c(database().query<int>(DB_MinRenlSpecAmt ));
+ MinRenlBaseSpecAmt =
round_specamt().c(database().query<int>(DB_MinRenlBaseSpecAmt));
database().query_into(DB_NoLapseDboLvlOnly , NoLapseDboLvlOnly);
database().query_into(DB_NoLapseUnratedOnly , NoLapseUnratedOnly);
database().query_into(DB_DboChgCanIncrSpecAmt , OptChgCanIncrSA);
@@ -585,7 +585,7 @@ void BasicValues::SetPermanentInvariants()
database().query_into(DB_MinPremType , MinPremType);
database().query_into(DB_TgtPremType , TgtPremType);
database().query_into(DB_TgtPremFixedAtIssue , TgtPremFixedAtIssue);
- TgtPremMonthlyPolFee =
currency(database().query<int>(DB_TgtPremMonthlyPolFee));
+ TgtPremMonthlyPolFee =
round_gross_premium().c(database().query<int>(DB_TgtPremMonthlyPolFee));
// Assertion: see comments on GetModalPremTgtFromTable().
LMI_ASSERT(C0 == TgtPremMonthlyPolFee || oe_modal_table == TgtPremType);
database().query_into(DB_CurrCoiTable0Limit , CurrCoiTable0Limit);
@@ -611,8 +611,8 @@ void BasicValues::SetPermanentInvariants()
// AdbLimit = database().query<int>(DB_AdbLimit );
// WpLimit = database().query<int>(DB_WpLimit );
// SpecAmtLoadLimit = database().query<int>(DB_SpecAmtLoadLimit);
- MinWD = currency(database().query<int>(DB_MinWd ));
- WDFee = currency(database().query<int>(DB_WdFee ));
+ MinWD = round_withdrawal().c(database().query<int>(DB_MinWd));
+ WDFee = round_withdrawal().c(database().query<int>(DB_WdFee));
database().query_into(DB_WdFeeRate , WDFeeRate);
database().query_into(DB_AllowChangeToDbo2 , AllowChangeToDBO2);
database().query_into(DB_AllowSpecAmtIncr , AllowSAIncr);
@@ -720,7 +720,7 @@ void BasicValues::SetPermanentInvariants()
database().query_into(DB_Effective7702DboRop, Effective7702DboRop);
TermIsDbFor7702 = oe_7702_term_is_db ==
database().query<oenum_7702_term>(DB_TermIsQABOrDb7702 );
TermIsDbFor7702A = oe_7702_term_is_db ==
database().query<oenum_7702_term>(DB_TermIsQABOrDb7702A);
- MaxNAAR = currency(yare_input_.MaximumNaar);
+ MaxNAAR = round_naar().c(yare_input_.MaximumNaar);
database().query_into(DB_MinPremIntSpread, MinPremIntSpread_);
}
diff --git a/loads_impl.hpp b/loads_impl.hpp
index 5cb3154..47a7e1c 100644
--- a/loads_impl.hpp
+++ b/loads_impl.hpp
@@ -68,7 +68,11 @@ class product_database;
/// However, if the monthly policy fee is $3.25 (current) and $5.00
/// (guaranteed), the midpoint mustn't be $4.125, because subtracting
/// that from the account value would make it a non-integral number
-/// of cents.
+/// of cents. An argument could be made for using a gross-premium
+/// rounding rule instead, reasoning that a policy fee ought to be
+/// independently payable, but the minutiae rule is likely to specify
+/// finer (or no different) rounding, which seems better for the
+/// midpoint case.
///
/// VectorExtraCompLoad_: Input extra load per dollar of premium.
///
- [lmi-commits] [lmi] valyuta/004 updated (cf62b44 -> 506051a), Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 260857d 2/9: Read product data files earlier, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 296ee07 5/9: Set 7702 and 7702A interest rates OAOO, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 288c26f 8/9: Refactor to avoid a header-only implementation, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 4a1687e 1/9: Expunge a defect marker [324], Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 50ed405 3/9: Prefer explicit to implicit currency rounding,
Greg Chicares <=
- [lmi-commits] [lmi] valyuta/004 9e6c7e1 4/9: Abjure converting currency ctors, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 806f2fd 6/9: fixup, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 87f1e13 7/9: Split a unit-test TU in twain, Greg Chicares, 2020/12/29
- [lmi-commits] [lmi] valyuta/004 506051a 9/9: Conditionally use H.R. 6800's 7702 transitional rates, Greg Chicares, 2020/12/29