Kaydet (Commit) e38d20c1 authored tarafından Kohei Yoshida's avatar Kohei Yoshida

Handle range references for group calculation. This is still untested.

Change-Id: I1eb1c217db66615028faa85720838579056dc150
üst f07601a2
...@@ -12,11 +12,11 @@ ...@@ -12,11 +12,11 @@
namespace formula { namespace formula {
SingleVectorRefToken::SingleVectorRefToken( const double* pArray, size_t nLength ) : SingleVectorRefToken::SingleVectorRefToken( const double* pArray, size_t nLength ) :
FormulaToken(svSingleVectorRef, ocPush), mpArray(pArray), mnLength(nLength) {} FormulaToken(svSingleVectorRef, ocPush), mpArray(pArray), mnArrayLength(nLength) {}
FormulaToken* SingleVectorRefToken::Clone() const FormulaToken* SingleVectorRefToken::Clone() const
{ {
return new SingleVectorRefToken(mpArray, mnLength); return new SingleVectorRefToken(mpArray, mnArrayLength);
} }
const double* SingleVectorRefToken::GetArray() const const double* SingleVectorRefToken::GetArray() const
...@@ -24,19 +24,19 @@ const double* SingleVectorRefToken::GetArray() const ...@@ -24,19 +24,19 @@ const double* SingleVectorRefToken::GetArray() const
return mpArray; return mpArray;
} }
size_t SingleVectorRefToken::GetLength() const size_t SingleVectorRefToken::GetArrayLength() const
{ {
return mnLength; return mnArrayLength;
} }
DoubleVectorRefToken::DoubleVectorRefToken( DoubleVectorRefToken::DoubleVectorRefToken(
const std::vector<const double*>& rArrays, size_t nRowSize, bool bAbsStart, bool bAbsEnd ) : const std::vector<const double*>& rArrays, size_t nArrayLength, size_t nRefRowSize, bool bStartFixed, bool bEndFixed ) :
FormulaToken(svDoubleVectorRef, ocPush), FormulaToken(svDoubleVectorRef, ocPush),
maArrays(rArrays), mnRowSize(nRowSize), mbAbsStart(bAbsStart), mbAbsEnd(bAbsEnd) {} maArrays(rArrays), mnArrayLength(nArrayLength), mnRefRowSize(nRefRowSize), mbStartFixed(bStartFixed), mbEndFixed(bEndFixed) {}
FormulaToken* DoubleVectorRefToken::Clone() const FormulaToken* DoubleVectorRefToken::Clone() const
{ {
return new DoubleVectorRefToken(maArrays, mnRowSize, mbAbsStart, mbAbsEnd); return new DoubleVectorRefToken(maArrays, mnArrayLength, mnRefRowSize, mbStartFixed, mbEndFixed);
} }
const std::vector<const double*>& DoubleVectorRefToken::GetArrays() const const std::vector<const double*>& DoubleVectorRefToken::GetArrays() const
...@@ -44,6 +44,26 @@ const std::vector<const double*>& DoubleVectorRefToken::GetArrays() const ...@@ -44,6 +44,26 @@ const std::vector<const double*>& DoubleVectorRefToken::GetArrays() const
return maArrays; return maArrays;
} }
size_t DoubleVectorRefToken::GetArrayLength() const
{
return mnArrayLength;
}
size_t DoubleVectorRefToken::GetRefRowSize() const
{
return mnRefRowSize;
}
bool DoubleVectorRefToken::IsStartFixed() const
{
return mbStartFixed;
}
bool DoubleVectorRefToken::IsEndFixed() const
{
return mbEndFixed;
}
} }
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
...@@ -17,7 +17,7 @@ namespace formula { ...@@ -17,7 +17,7 @@ namespace formula {
class FORMULA_DLLPUBLIC SingleVectorRefToken : public FormulaToken class FORMULA_DLLPUBLIC SingleVectorRefToken : public FormulaToken
{ {
const double* mpArray; const double* mpArray;
size_t mnLength; size_t mnArrayLength;
public: public:
SingleVectorRefToken( const double* pArray, size_t nLength ); SingleVectorRefToken( const double* pArray, size_t nLength );
...@@ -25,7 +25,7 @@ public: ...@@ -25,7 +25,7 @@ public:
virtual FormulaToken* Clone() const; virtual FormulaToken* Clone() const;
const double* GetArray() const; const double* GetArray() const;
size_t GetLength() const; size_t GetArrayLength() const;
}; };
/** /**
...@@ -36,18 +36,23 @@ class FORMULA_DLLPUBLIC DoubleVectorRefToken : public FormulaToken ...@@ -36,18 +36,23 @@ class FORMULA_DLLPUBLIC DoubleVectorRefToken : public FormulaToken
{ {
std::vector<const double*> maArrays; std::vector<const double*> maArrays;
size_t mnRowSize; size_t mnArrayLength;
size_t mnRefRowSize;
bool mbAbsStart:1; /// whether or not the start row position is absolute. bool mbStartFixed:1; /// whether or not the start row position is absolute.
bool mbAbsEnd:1; /// whether or not the end row position is absolute. bool mbEndFixed:1; /// whether or not the end row position is absolute.
public: public:
DoubleVectorRefToken( DoubleVectorRefToken(
const std::vector<const double*>& rArrays, size_t nRowSize, bool bAbsStart, bool bAbsEnd ); const std::vector<const double*>& rArrays, size_t nArrayLength, size_t nRefRowSize, bool bStartFixed, bool bEndFixed );
virtual FormulaToken* Clone() const; virtual FormulaToken* Clone() const;
const std::vector<const double*>& GetArrays() const; const std::vector<const double*>& GetArrays() const;
size_t GetArrayLength() const;
size_t GetRefRowSize() const;
bool IsStartFixed() const;
bool IsEndFixed() const;
}; };
} }
......
...@@ -3030,24 +3030,25 @@ bool ScFormulaCell::InterpretFormulaGroup() ...@@ -3030,24 +3030,25 @@ bool ScFormulaCell::InterpretFormulaGroup()
size_t nCols = aRef.Ref2.nCol - aRef.Ref1.nCol + 1; size_t nCols = aRef.Ref2.nCol - aRef.Ref1.nCol + 1;
std::vector<const double*> aArrays; std::vector<const double*> aArrays;
aArrays.reserve(nCols); aArrays.reserve(nCols);
SCROW nLength = xGroup->mnLength; SCROW nArrayLength = xGroup->mnLength;
SCROW nRefRowSize = aRef.Ref2.nRow - aRef.Ref1.nRow + 1;
if (!bAbsLast) if (!bAbsLast)
{ {
// range end position is relative. Extend it. // range end position is relative. Extend the array length.
nLength += aRef.Ref2.nRow - aRef.Ref1.nRow; nArrayLength += nRefRowSize - 1;
} }
for (SCCOL i = aRef.Ref1.nCol; i <= aRef.Ref2.nCol; ++i) for (SCCOL i = aRef.Ref1.nCol; i <= aRef.Ref2.nCol; ++i)
{ {
aRefPos.SetCol(i); aRefPos.SetCol(i);
const double* pArray = pDocument->FetchDoubleArray(aCxt, aRefPos, nLength); const double* pArray = pDocument->FetchDoubleArray(aCxt, aRefPos, nArrayLength);
if (!pArray) if (!pArray)
return false; return false;
aArrays.push_back(pArray); aArrays.push_back(pArray);
} }
formula::DoubleVectorRefToken aTok(aArrays, nLength, bAbsFirst, bAbsLast); formula::DoubleVectorRefToken aTok(aArrays, nArrayLength, nRefRowSize, bAbsFirst, bAbsLast);
aCode.AddToken(aTok); aCode.AddToken(aTok);
} }
else else
...@@ -3088,11 +3089,37 @@ bool ScFormulaCell::InterpretFormulaGroup() ...@@ -3088,11 +3089,37 @@ bool ScFormulaCell::InterpretFormulaGroup()
{ {
const formula::SingleVectorRefToken* p2 = static_cast<const formula::SingleVectorRefToken*>(p); const formula::SingleVectorRefToken* p2 = static_cast<const formula::SingleVectorRefToken*>(p);
const double* pArray = p2->GetArray(); const double* pArray = p2->GetArray();
aCode2.AddDouble(pArray[i]); aCode2.AddDouble(i < p2->GetArrayLength() ? pArray[i] : 0.0);
} }
break; break;
case svDoubleVectorRef: case svDoubleVectorRef:
return false; {
const formula::DoubleVectorRefToken* p2 = static_cast<const formula::DoubleVectorRefToken*>(p);
const std::vector<const double*>& rArrays = p2->GetArrays();
size_t nColSize = rArrays.size();
size_t nRowStart = p2->IsStartFixed() ? 0 : i;
size_t nRowEnd = p2->GetRefRowSize() - 1;
if (!p2->IsEndFixed())
nRowEnd += i;
size_t nRowSize = nRowEnd - nRowStart + 1;
ScMatrixRef pMat(new ScMatrix(nColSize, nRowSize, 0.0));
for (size_t nCol = 0; nCol < nColSize; ++nCol)
{
const double* pArray = rArrays[nCol];
for (size_t nRow = 0; nRow < nRowSize; ++nRow)
{
if (nRowStart + nRow < p2->GetArrayLength())
{
double fVal = pArray[nRowStart+nRow];
pMat->PutDouble(fVal, nCol, nRow);
}
}
}
ScMatrixToken aTok(pMat);
aCode2.AddToken(aTok);
}
break; break;
default: default:
aCode2.AddToken(*p); aCode2.AddToken(*p);
......
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