don't bother scanning nonexistent data (tdf#141182)

There's no point scanning for non-empty cells after the last data
cell, and this avoids processing mdds structures (such as repeated
creating of flat_segment_tree).

Change-Id: Ibec324aa2de457e8439c38a561f55ced9f478899
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/131059
Tested-by: Jenkins
Reviewed-by: Luboš Luňák <l.lunak@collabora.com>
diff --git a/sc/source/core/data/column3.cxx b/sc/source/core/data/column3.cxx
index 618e56e..3190328 100644
--- a/sc/source/core/data/column3.cxx
+++ b/sc/source/core/data/column3.cxx
@@ -92,6 +92,8 @@ void ScColumn::BroadcastCells( const std::vector<SCROW>& rRows, SfxHintId nHint 

void ScColumn::BroadcastRows( SCROW nStartRow, SCROW nEndRow, SfxHintId nHint )
{
    if( nStartRow > GetLastDataPos())
        return;
    sc::SingleColumnSpanSet aSpanSet(GetDoc().GetSheetLimits());
    aSpanSet.scan(*this, nStartRow, nEndRow);
    std::vector<SCROW> aRows;
diff --git a/sc/source/core/data/columnspanset.cxx b/sc/source/core/data/columnspanset.cxx
index 7a4d90f..eb09ea2 100644
--- a/sc/source/core/data/columnspanset.cxx
+++ b/sc/source/core/data/columnspanset.cxx
@@ -25,12 +25,12 @@ namespace sc {

namespace {

class ColumnScanner
class ColumnNonEmptyRangesScanner
{
    ColumnSpanSet::ColumnSpansType& mrRanges;
    bool mbVal;
public:
    ColumnScanner(ColumnSpanSet::ColumnSpansType& rRanges, bool bVal) :
    ColumnNonEmptyRangesScanner(ColumnSpanSet::ColumnSpansType& rRanges, bool bVal) :
        mrRanges(rRanges), mbVal(bVal) {}

    void operator() (const sc::CellStoreType::value_type& node, size_t nOffset, size_t nDataSize)
@@ -137,7 +137,10 @@ void ColumnSpanSet::scan(

        const CellStoreType& rSrcCells = pTab->aCol[nCol].maCells;

        ColumnScanner aScanner(rCol.maSpans, bVal);
        if( nRow1 > pTab->aCol[nCol].GetLastDataPos())
            continue;

        ColumnNonEmptyRangesScanner aScanner(rCol.maSpans, bVal);
        ParseBlock(rSrcCells.begin(), rSrcCells, aScanner, nRow1, nRow2);
    }
}
@@ -219,11 +222,11 @@ void ColumnSpanSet::executeColumnAction(ScDocument& rDoc, ColumnAction& ac) cons

namespace {

class Scanner
class NonEmptyRangesScanner
{
    SingleColumnSpanSet::ColumnSpansType& mrRanges;
public:
    explicit Scanner(SingleColumnSpanSet::ColumnSpansType& rRanges) : mrRanges(rRanges) {}
    explicit NonEmptyRangesScanner(SingleColumnSpanSet::ColumnSpansType& rRanges) : mrRanges(rRanges) {}

    void operator() (const sc::CellStoreType::value_type& node, size_t nOffset, size_t nDataSize)
    {
@@ -258,16 +261,20 @@ void SingleColumnSpanSet::scan(const ScColumn& rColumn)

void SingleColumnSpanSet::scan(const ScColumn& rColumn, SCROW nStart, SCROW nEnd)
{
    if( nStart > rColumn.GetLastDataPos())
        return;
    const CellStoreType& rCells = rColumn.maCells;
    Scanner aScanner(maSpans);
    NonEmptyRangesScanner aScanner(maSpans);
    sc::ParseBlock(rCells.begin(), rCells, aScanner, nStart, nEnd);
}

void SingleColumnSpanSet::scan(
    ColumnBlockConstPosition& rBlockPos, const ScColumn& rColumn, SCROW nStart, SCROW nEnd)
{
    if( nStart > rColumn.GetLastDataPos())
        return;
    const CellStoreType& rCells = rColumn.maCells;
    Scanner aScanner(maSpans);
    NonEmptyRangesScanner aScanner(maSpans);
    rBlockPos.miCellPos = sc::ParseBlock(rBlockPos.miCellPos, rCells, aScanner, nStart, nEnd);
}