diff options
-rw-r--r-- | sc/qa/unit/ucalc.hxx | 2 | ||||
-rw-r--r-- | sc/qa/unit/ucalc_formula.cxx | 34 | ||||
-rw-r--r-- | sc/source/core/data/formulacell.cxx | 4 |
3 files changed, 40 insertions, 0 deletions
diff --git a/sc/qa/unit/ucalc.hxx b/sc/qa/unit/ucalc.hxx index 1a2ded57017f..feb5761305f0 100644 --- a/sc/qa/unit/ucalc.hxx +++ b/sc/qa/unit/ucalc.hxx @@ -220,6 +220,7 @@ public: void testMatConcatReplication(); void testRefR1C1WholeCol(); void testRefR1C1WholeRow(); + void testIterations(); void testExternalRef(); void testExternalRefFunctions(); @@ -614,6 +615,7 @@ public: CPPUNIT_TEST(testFuncGETPIVOTDATALeafAccess); CPPUNIT_TEST(testRefR1C1WholeCol); CPPUNIT_TEST(testRefR1C1WholeRow); + CPPUNIT_TEST(testIterations); CPPUNIT_TEST(testMatrixOp); CPPUNIT_TEST(testFuncRangeOp); CPPUNIT_TEST(testFuncFORMULA); diff --git a/sc/qa/unit/ucalc_formula.cxx b/sc/qa/unit/ucalc_formula.cxx index 0c9fdde78b80..a6af03344b84 100644 --- a/sc/qa/unit/ucalc_formula.cxx +++ b/sc/qa/unit/ucalc_formula.cxx @@ -8361,4 +8361,38 @@ void Test::testFuncRefListArraySUBTOTAL() m_pDoc->DeleteTab(0); } +// Test iterations with circular chain of references. +void Test::testIterations() +{ + ScDocOptions aDocOpts = m_pDoc->GetDocOptions(); + aDocOpts.SetIter( true ); + m_pDoc->SetDocOptions( aDocOpts ); + + m_pDoc->InsertTab(0, "Test"); + + m_pDoc->SetValue( 0, 0, 0, 0.01 ); // A1 + m_pDoc->SetString( 0, 1, 0, "=A1" ); // A2 + m_pDoc->SetString( 0, 2, 0, "=COS(A2)" ); // A3 + m_pDoc->CalcAll(); + + // Establish reference cycle for the computation of the fixed point of COS() function + m_pDoc->SetString( 0, 0, 0, "=A3" ); // A1 + m_pDoc->CalcAll(); + + CPPUNIT_ASSERT_EQUAL_MESSAGE( "Cell A3 should not have any formula error", FormulaError::NONE, m_pDoc->GetErrCode( ScAddress( 0, 2, 0) ) ); + CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE( "Iterations to calculate fixed point of cos() failed", 0.7387, m_pDoc->GetValue(0, 2, 0), 1e-4 ); + + // Modify the formula + m_pDoc->SetString( 0, 2, 0, "=COS(A2)+0.001" ); // A3 + m_pDoc->CalcAll(); + + CPPUNIT_ASSERT_EQUAL_MESSAGE( "Cell A3 should not have any formula error after perturbation", FormulaError::NONE, m_pDoc->GetErrCode( ScAddress( 0, 2, 0) ) ); + CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE( "Iterations to calculate perturbed fixed point of cos() failed", 0.7399, m_pDoc->GetValue(0, 2, 0), 1e-4 ); + + m_pDoc->DeleteTab(0); + + aDocOpts.SetIter( false ); + m_pDoc->SetDocOptions( aDocOpts ); +} + /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sc/source/core/data/formulacell.cxx b/sc/source/core/data/formulacell.cxx index c0a363c78a5a..c45c4c0bcedb 100644 --- a/sc/source/core/data/formulacell.cxx +++ b/sc/source/core/data/formulacell.cxx @@ -1790,6 +1790,10 @@ void ScFormulaCell::InterpretTail( ScInterpretTailParameter eTailParam ) { if (nSeenInIteration > 0) --nSeenInIteration; // retry when iteration is resumed + + if ( aResult.GetType() == formula::svUnknown ) + aResult.SetToken( pInterpreter->GetResultToken().get() ); + return; } bRunning = bOldRunning; |