[Libreoffice-commits] core.git: sc/inc sc/source

Łukasz Hryniuk lukasz.hryniuk at wp.pl
Thu Oct 1 22:09:48 PDT 2015


 sc/inc/scmatrix.hxx              |    4 +
 sc/source/core/tool/scmatrix.cxx |  156 +++++++++++++++++++++++++++------------
 2 files changed, 113 insertions(+), 47 deletions(-)

New commits:
commit 9f162251c6ef672a2c7178af1463c2b13dd136de
Author: Łukasz Hryniuk <lukasz.hryniuk at wp.pl>
Date:   Sat Aug 8 15:47:19 2015 +0200

    Add WalkElementBlocksMultipleValues and remove Ops
    
    WalkElementBlocksMultipleValues class is able to collect a few values at
    once. scmatrix.cxx were moved to matrixoperators.cxx
    
    Change-Id: Id069f89a58cce046fb3d4ddf6f49db0452bdfb36
    Reviewed-on: https://gerrit.libreoffice.org/17593
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Markus Mohrhard <markus.mohrhard at googlemail.com>
    Tested-by: Markus Mohrhard <markus.mohrhard at googlemail.com>

diff --git a/sc/inc/scmatrix.hxx b/sc/inc/scmatrix.hxx
index bd28944..db863cc 100644
--- a/sc/inc/scmatrix.hxx
+++ b/sc/inc/scmatrix.hxx
@@ -21,12 +21,16 @@
 #define INCLUDED_SC_INC_SCMATRIX_HXX
 
 #include "global.hxx"
+#include "matrixoperators.hxx"
 #include "types.hxx"
 #include <formula/errorcodes.hxx>
 #include "scdllapi.h"
 #include <rtl/ustring.hxx>
 #include <svl/sharedstring.hxx>
 
+#include <functional>
+#include <utility>
+#include <vector>
 #include <boost/intrusive_ptr.hpp>
 #include <boost/interprocess/smart_ptr/unique_ptr.hpp>
 
diff --git a/sc/source/core/tool/scmatrix.cxx b/sc/source/core/tool/scmatrix.cxx
index 5ef8378..207e451 100644
--- a/sc/source/core/tool/scmatrix.cxx
+++ b/sc/source/core/tool/scmatrix.cxx
@@ -24,6 +24,7 @@
 #include "interpre.hxx"
 #include "mtvelements.hxx"
 #include "compare.hxx"
+#include "matrixoperators.hxx"
 #include "math.hxx"
 
 #include <boost/noncopyable.hpp>
@@ -999,47 +1000,10 @@ double ScMatrixImpl::Xor() const
 
 namespace {
 
-struct SumOp
-{
-    static const double InitVal;
-
-    void operator() (double& rAccum, double fVal)
-    {
-        rAccum += fVal;
-    }
-};
-
-const double SumOp::InitVal = 0.0;
-
-struct SumSquareOp
-{
-    static const double InitVal;
-
-    void operator() (double& rAccum, double fVal)
-    {
-        rAccum += fVal*fVal;
-    }
-};
-
-const double SumSquareOp::InitVal = 0.0;
-
-struct ProductOp
-{
-    static const double InitVal;
-
-    void operator() (double& rAccum, double fVal)
-    {
-        rAccum *= fVal;
-    }
-};
-
-const double ProductOp::InitVal = 1.0;
-
 template<typename _Op>
-class WalkElementBlocks : std::unary_function<MatrixImplType::element_block_node_type, void>
+class WalkElementBlocks
 {
     _Op maOp;
-
     ScMatrix::IterateResult maRes;
     bool mbFirst:1;
     bool mbTextAsZero:1;
@@ -1066,7 +1030,9 @@ public:
                         mbFirst = false;
                     }
                     else
+                    {
                         maOp(maRes.mfRest, *it);
+                    }
                 }
                 maRes.mnCount += node.size;
             }
@@ -1085,7 +1051,9 @@ public:
                         mbFirst = false;
                     }
                     else
+                    {
                         maOp(maRes.mfRest, *it);
+                    }
                 }
                 maRes.mnCount += node.size;
             }
@@ -1101,6 +1069,95 @@ public:
     }
 };
 
+template<typename _Op>
+class WalkElementBlocksMultipleValues
+{
+    const std::vector<std::unique_ptr<_Op>>& maOp;
+    std::vector<ScMatrix::IterateResult> maRes;
+    bool mbFirst:1;
+    bool mbTextAsZero:1;
+public:
+    WalkElementBlocksMultipleValues(bool bTextAsZero, const std::vector<std::unique_ptr<_Op>>& aOp) :
+        maOp(aOp), mbFirst(true), mbTextAsZero(bTextAsZero)
+    {
+        for (const auto& pOp : maOp)
+        {
+            maRes.emplace_back(pOp->mInitVal, pOp->mInitVal, 0);
+        }
+        maRes.emplace_back(0.0, 0.0, 0); // count
+    }
+
+    const std::vector<ScMatrix::IterateResult>& getResult() const { return maRes; }
+
+    void operator() (const MatrixImplType::element_block_node_type& node)
+    {
+        switch (node.type)
+        {
+            case mdds::mtm::element_numeric:
+            {
+                typedef MatrixImplType::numeric_block_type block_type;
+
+                block_type::const_iterator it = block_type::begin(*node.data);
+                block_type::const_iterator itEnd = block_type::end(*node.data);
+                for (; it != itEnd; ++it)
+                {
+                    if (mbFirst)
+                    {
+                        for (auto i = 0u; i < maOp.size(); ++i)
+                        {
+                            (*maOp[i])(maRes[i].mfFirst, *it);
+                        }
+                        mbFirst = false;
+                    }
+                    else
+                    {
+                        for (auto i = 0u; i < maOp.size(); ++i)
+                        {
+                            (*maOp[i])(maRes[i].mfRest, *it);
+                        }
+                    }
+                }
+                maRes.back().mnCount += node.size;
+            }
+            break;
+            case mdds::mtm::element_boolean:
+            {
+                typedef MatrixImplType::boolean_block_type block_type;
+
+                block_type::const_iterator it = block_type::begin(*node.data);
+                block_type::const_iterator itEnd = block_type::end(*node.data);
+                for (; it != itEnd; ++it)
+                {
+                    if (mbFirst)
+                    {
+                        for (auto i = 0u; i < maOp.size(); ++i)
+                        {
+                            (*maOp[i])(maRes[i].mfFirst, *it);
+                        }
+                        mbFirst = false;
+                    }
+                    else
+                    {
+                        for (auto i = 0u; i < maOp.size(); ++i)
+                        {
+                            (*maOp[i])(maRes[i].mfRest, *it);
+                        }
+                    }
+                }
+                maRes.back().mnCount += node.size;
+            }
+            break;
+            case mdds::mtm::element_string:
+                if (mbTextAsZero)
+                    maRes.back().mnCount += node.size;
+            break;
+            case mdds::mtm::element_empty:
+            default:
+                ;
+        }
+    }
+};
+
 class CountElements : std::unary_function<MatrixImplType::element_block_node_type, void>
 {
     size_t mnCount;
@@ -1697,26 +1754,31 @@ public:
 
 }
 
-ScMatrix::IterateResult ScMatrixImpl::Sum(bool bTextAsZero) const
+namespace {
+
+template<typename TOp>
+ScMatrix::IterateResult GetValueWithCount(bool bTextAsZero, const MatrixImplType& maMat)
 {
-    WalkElementBlocks<SumOp> aFunc(bTextAsZero);
+    WalkElementBlocks<TOp> aFunc(bTextAsZero);
     maMat.walk(aFunc);
     return aFunc.getResult();
 }
 
+}
+
+ScMatrix::IterateResult ScMatrixImpl::Sum(bool bTextAsZero) const
+{
+    return GetValueWithCount<sc::op::Sum>(bTextAsZero, maMat);
+}
+
 ScMatrix::IterateResult ScMatrixImpl::SumSquare(bool bTextAsZero) const
 {
-    WalkElementBlocks<SumSquareOp> aFunc(bTextAsZero);
-    maMat.walk(aFunc);
-    return aFunc.getResult();
+    return GetValueWithCount<sc::op::SumSquare>(bTextAsZero, maMat);
 }
 
 ScMatrix::IterateResult ScMatrixImpl::Product(bool bTextAsZero) const
 {
-    WalkElementBlocks<ProductOp> aFunc(bTextAsZero);
-    maMat.walk(aFunc);
-    ScMatrix::IterateResult aRes = aFunc.getResult();
-    return aRes;
+    return GetValueWithCount<sc::op::Product>(bTextAsZero, maMat);
 }
 
 size_t ScMatrixImpl::Count(bool bCountStrings) const


More information about the Libreoffice-commits mailing list