From cffba76a3487628f0557b423cefe150932308ede Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 12 Jul 2013 11:40:54 -0400 Subject: Cache select converted tokens to avoid unnecessary token duplication. Change-Id: I3a63d5cbbc1cdc37d681ffd41ec22ff65e56cc0d --- sc/source/core/tool/formulagroup.cxx | 27 +++++++++++++++++++++++++-- 1 file changed, 25 insertions(+), 2 deletions(-) (limited to 'sc') diff --git a/sc/source/core/tool/formulagroup.cxx b/sc/source/core/tool/formulagroup.cxx index 6573d1544405..4ac4b6be8112 100644 --- a/sc/source/core/tool/formulagroup.cxx +++ b/sc/source/core/tool/formulagroup.cxx @@ -19,6 +19,7 @@ #include "formula/vectortoken.hxx" #include +#include #define USE_DUMMY_INTERPRETER 1 @@ -37,6 +38,8 @@ bool FormulaGroupInterpreterSoftware::interpret(ScDocument& rDoc, const ScAddres const ScFormulaCellGroupRef& xGroup, ScTokenArray& rCode) { + typedef boost::unordered_map CachedTokensType; + // Decompose the group into individual cells and calculate them individually. // The caller must ensure that the top position is the start position of @@ -45,11 +48,21 @@ bool FormulaGroupInterpreterSoftware::interpret(ScDocument& rDoc, const ScAddres ScAddress aTmpPos = rTopPos; std::vector aResults; aResults.reserve(xGroup->mnLength); + CachedTokensType aCachedTokens; + for (SCROW i = 0; i < xGroup->mnLength; ++i, aTmpPos.IncRow()) { ScTokenArray aCode2; for (const formula::FormulaToken* p = rCode.First(); p; p = rCode.Next()) { + CachedTokensType::iterator it = aCachedTokens.find(p); + if (it != aCachedTokens.end()) + { + // This token is cached. Use the cached one. + aCode2.AddToken(*it->second); + continue; + } + switch (p->GetType()) { case formula::svSingleVectorRef: @@ -77,8 +90,18 @@ bool FormulaGroupInterpreterSoftware::interpret(ScDocument& rDoc, const ScAddres pMat->PutDouble(pArray, nRowSize, nCol, 0); } - ScMatrixToken aTok(pMat); - aCode2.AddToken(aTok); + if (p2->IsStartFixed() && p2->IsEndFixed()) + { + // Cached the converted token for absolute range referene. + formula::FormulaTokenRef xTok(new ScMatrixToken(pMat)); + aCachedTokens.insert(CachedTokensType::value_type(p, xTok)); + aCode2.AddToken(*xTok); + } + else + { + ScMatrixToken aTok(pMat); + aCode2.AddToken(aTok); + } } break; default: -- cgit