summaryrefslogtreecommitdiff
path: root/sc
diff options
context:
space:
mode:
authorMichael Meeks <michael.meeks@collabora.com>2014-10-30 22:51:59 +0000
committerMichael Meeks <michael.meeks@collabora.com>2014-11-05 21:09:17 +0000
commit11a35bd6e951f151353f9129bb74d06b90227bc6 (patch)
treee0888c1e49bbb230a499c8b6176df79321fa3523 /sc
parentffdf0ed4cd76188e780eceee4333f90a00217f9d (diff)
Thread excel table row/column format finalization.
Change-Id: I6ddc0270831989291893b170d57fea14329a26ba
Diffstat (limited to 'sc')
-rw-r--r--sc/source/filter/excel/xetable.cxx60
-rw-r--r--sc/source/filter/inc/xetable.hxx3
2 files changed, 55 insertions, 8 deletions
diff --git a/sc/source/filter/excel/xetable.cxx b/sc/source/filter/excel/xetable.cxx
index cae6460d61ff..770f30e5a9ff 100644
--- a/sc/source/filter/excel/xetable.cxx
+++ b/sc/source/filter/excel/xetable.cxx
@@ -34,6 +34,8 @@
#include "xeescher.hxx"
#include "xeextlst.hxx"
#include "tokenarray.hxx"
+#include <thread>
+#include <comphelper/threadpool.hxx>
using namespace ::oox;
@@ -1777,7 +1779,7 @@ void XclExpRow::AppendCell( XclExpCellRef xCell, bool bIsMergedBase )
InsertCell( xCell, maCellList.GetSize(), bIsMergedBase );
}
-void XclExpRow::Finalize( const ScfUInt16Vec& rColXFIndexes )
+void XclExpRow::Finalize( const ScfUInt16Vec& rColXFIndexes, bool bProgress )
{
size_t nPos, nSize;
@@ -1911,10 +1913,10 @@ void XclExpRow::Finalize( const ScfUInt16Vec& rColXFIndexes )
++nPos;
}
- // progress bar includes disabled rows
- GetProgressBar().Progress();
+ // progress bar includes disabled rows; only update it in the lead thread.
+ if (bProgress)
+ GetProgressBar().Progress();
}
-
sal_uInt16 XclExpRow::GetFirstUsedXclCol() const
{
return maCellList.IsEmpty() ? 0 : maCellList.GetFirstRecord()->GetXclCol();
@@ -2038,15 +2040,58 @@ void XclExpRowBuffer::CreateRows( SCROW nFirstFreeScRow )
GetOrCreateRow( ::std::max ( nFirstFreeScRow - 1, GetMaxPos().Row() ), true );
}
+class RowFinalizeTask : public comphelper::ThreadTask
+{
+ bool mbProgress;
+ const ScfUInt16Vec& mrColXFIndexes;
+ std::vector< XclExpRow * > maRows;
+public:
+ RowFinalizeTask( const ScfUInt16Vec& rColXFIndexes,
+ bool bProgress ) :
+ mbProgress( bProgress ),
+ mrColXFIndexes( rColXFIndexes ) {}
+ virtual ~RowFinalizeTask() {}
+ void push_back( XclExpRow *pRow ) { maRows.push_back( pRow ); }
+ virtual void doWork()
+ {
+ for (size_t i = 0; i < maRows.size(); i++ )
+ maRows[ i ]->Finalize( mrColXFIndexes, mbProgress );
+ }
+};
+
void XclExpRowBuffer::Finalize( XclExpDefaultRowData& rDefRowData, const ScfUInt16Vec& rColXFIndexes )
{
// *** Finalize all rows *** ----------------------------------------------
GetProgressBar().ActivateFinalRowsSegment();
- RowMap::iterator itr, itrBeg = maRowMap.begin(), itrEnd = maRowMap.end();
- for (itr = itrBeg; itr != itrEnd; ++itr)
- itr->second->Finalize(rColXFIndexes);
+ // This is staggeringly slow, and each element operates only
+ // on its own data.
+ size_t nRows = maRowMap.size();
+ size_t nThreads = std::max( std::thread::hardware_concurrency(), 1U );
+ if ( nThreads == 1 || nRows < 128 )
+ {
+ RowMap::iterator itr, itrBeg = maRowMap.begin(), itrEnd = maRowMap.end();
+ for (itr = itrBeg; itr != itrEnd; ++itr)
+ itr->second->Finalize( rColXFIndexes, true );
+ }
+ else
+ {
+ comphelper::ThreadPool &rPool = comphelper::ThreadPool::getSharedOptimalPool();
+ std::vector<RowFinalizeTask*> pTasks(nThreads, NULL);
+ for ( size_t i = 0; i < nThreads; i++ )
+ pTasks[ i ] = new RowFinalizeTask( rColXFIndexes, i == 0 );
+
+ RowMap::iterator itr, itrBeg = maRowMap.begin(), itrEnd = maRowMap.end();
+ size_t nIdx = 0;
+ for ( itr = itrBeg; itr != itrEnd; ++itr, ++nIdx )
+ pTasks[ nIdx % nThreads ]->push_back( itr->second.get() );
+
+ for ( size_t i = 0; i < nThreads; i++ )
+ rPool.pushTask( pTasks[ i ] );
+
+ rPool.waitUntilEmpty();
+ }
// *** Default row format *** ---------------------------------------------
@@ -2059,6 +2104,7 @@ void XclExpRowBuffer::Finalize( XclExpDefaultRowData& rDefRowData, const ScfUInt
XclExpRow* pPrev = NULL;
typedef std::vector< XclExpRow* > XclRepeatedRows;
XclRepeatedRows aRepeated;
+ RowMap::iterator itr, itrBeg = maRowMap.begin(), itrEnd = maRowMap.end();
for (itr = itrBeg; itr != itrEnd; ++itr)
{
const RowRef& rRow = itr->second;
diff --git a/sc/source/filter/inc/xetable.hxx b/sc/source/filter/inc/xetable.hxx
index 081bdb4ae0f8..7fca5e45ee3e 100644
--- a/sc/source/filter/inc/xetable.hxx
+++ b/sc/source/filter/inc/xetable.hxx
@@ -857,7 +857,8 @@ public:
void AppendCell( XclExpCellRef xCell, bool bIsMergedBase );
/** Converts all XF identifiers into the Excel XF indexes. */
- void Finalize( const ScfUInt16Vec& rColXFIndexes );
+ void Finalize( const ScfUInt16Vec& rColXFIndexes,
+ bool bUpdateProgress );
/** Returns the column index of the first used cell in this row.
@descr This function can only be called after Finalize(). */