Kaydet (Commit) 9f1ffa64 authored tarafından Regina Henschel's avatar Regina Henschel Kaydeden (comit) Caolán McNamara

Resolves: #i95167# XIRR() function gives Err:502

Patch by: Driss Ben Zoubeir <driss.zoubeir@gmail.com>
Review by: Regina Henschel <rb.henschel@t-online.de>
(cherry picked from commit 85cd0721)

Conflicts:
	scaddins/source/analysis/financial.cxx

Change-Id: I385d5f9bfa840fe609cb5723f2d4d57d26fd0d6c
üst 4d48b51a
...@@ -541,16 +541,37 @@ double SAL_CALL AnalysisAddIn::getXirr( ...@@ -541,16 +541,37 @@ double SAL_CALL AnalysisAddIn::getXirr(
// Newton's method - try to find a fResultRate, so that lcl_sca_XirrResult() returns 0. // Newton's method - try to find a fResultRate, so that lcl_sca_XirrResult() returns 0.
sal_Int32 nIter = 0; sal_Int32 nIter = 0;
bool bContLoop; double fResultValue;
sal_Int32 nIterScan = 0;
bool bContLoop = false;
bool bResultRateScanEnd = false;
// First the inner while-loop will be executed using the default Value fResultRate
// or the user guessed fResultRate if those do not deliver a solution for the
// Newton's method then the range from -0.99 to +0.99 will be scanned with a
// step size of 0.01 to find fResultRate's value which can deliver a solution
do do
{ {
double fResultValue = lcl_sca_XirrResult( aValues, aDates, fResultRate ); if (nIterScan >=1)
double fNewRate = fResultRate - fResultValue / lcl_sca_XirrResult_Deriv1( aValues, aDates, fResultRate ); fResultRate = -0.99 + (nIterScan -1)* 0.01;
double fRateEps = fabs( fNewRate - fResultRate ); do
fResultRate = fNewRate; {
bContLoop = (fRateEps > fMaxEps) && (fabs( fResultValue ) > fMaxEps); fResultValue = lcl_sca_XirrResult( aValues, aDates, fResultRate );
double fNewRate = fResultRate - fResultValue / lcl_sca_XirrResult_Deriv1( aValues, aDates, fResultRate );
double fRateEps = fabs( fNewRate - fResultRate );
fResultRate = fNewRate;
bContLoop = (fRateEps > fMaxEps) && (fabs( fResultValue ) > fMaxEps);
}
while( bContLoop && (++nIter < nMaxIter) );
nIter = 0;
if ( ::rtl::math::isNan(fResultRate) || ::rtl::math::isInf(fResultRate)
||::rtl::math::isNan(fResultValue) || ::rtl::math::isInf(fResultValue))
bContLoop = true;
++nIterScan;
bResultRateScanEnd = (nIterScan >= 200);
} }
while( bContLoop && (++nIter < nMaxIter) ); while(bContLoop && !bResultRateScanEnd);
if( bContLoop ) if( bContLoop )
throw css::lang::IllegalArgumentException(); throw css::lang::IllegalArgumentException();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment