diff options
author | Ashod Nakashian <ashod.nakashian@collabora.co.uk> | 2016-06-19 12:13:35 -0400 |
---|---|---|
committer | Ashod Nakashian <ashnakash@gmail.com> | 2016-06-27 00:08:49 +0000 |
commit | 3464bb16e667d6cabcb02eaaeb07c6938eb9d7a5 (patch) | |
tree | c300730288807ab8a082754673a515d122db832f /sc | |
parent | c8a94cae37029b037507ce86d149ba56ca341f11 (diff) |
bccu#1893 - [PERFORMANCE] .uno:ViewRowColumnHeaders too slow
For very large spreadsheets, the boost json generator
(property_tree) is extremely slow and memory-inefficient.
There is little need for generic json generator, however,
since there are exactly two nodes (rows and columns)
and each is an array of size/text pairs.
The new logic uses a string with reserved capacity
to accomodate the output and generates it in one
step.
The speed improvement is orders of magnitude (hours to seconds)
for very large spreadsheets.
Reviewed-on: https://gerrit.libreoffice.org/26480
Reviewed-by: Ashod Nakashian <ashnakash@gmail.com>
Tested-by: Ashod Nakashian <ashnakash@gmail.com>
(cherry picked from commit c9d5ff919c87566fdbc6a2ddde0bcd30d471c425)
Change-Id: Ifaf316c270ed6e4b923ec44189a315f69e7e9b0e
Reviewed-on: https://gerrit.libreoffice.org/26485
Tested-by: Jenkins <ci@libreoffice.org>
Reviewed-by: Ashod Nakashian <ashnakash@gmail.com>
Diffstat (limited to 'sc')
-rw-r--r-- | sc/source/ui/view/tabview.cxx | 52 |
1 files changed, 29 insertions, 23 deletions
diff --git a/sc/source/ui/view/tabview.cxx b/sc/source/ui/view/tabview.cxx index e4671f6da2ed..be17b1f11bd2 100644 --- a/sc/source/ui/view/tabview.cxx +++ b/sc/source/ui/view/tabview.cxx @@ -2313,15 +2313,20 @@ OUString ScTabView::getRowColumnHeaders(const Rectangle& rRectangle) SCROW nEndRow = 0; pDoc->GetTiledRenderingArea(aViewData.GetTabNo(), nEndCol, nEndRow); - boost::property_tree::ptree aRows; + rtl::OUStringBuffer aBuffer(256 + (50 * nEndRow) + (50 * nEndCol)); + + aBuffer.append("{ \"commandName\": \".uno:ViewRowColumnHeaders\",\n"); + aBuffer.append("\"rows\": [\n"); + long nTotal = 0; long nTotalPixels = 0; + bool bFirstRow = true; for (SCROW nRow = 0; nRow <= nEndRow; ++nRow) { // nSize will be 0 for hidden rows. - sal_uInt16 nSize = pDoc->GetRowHeight(nRow, aViewData.GetTabNo()); - long nSizePixels = ScViewData::ToPixel(nSize, aViewData.GetPPTY()); - OUString aText = pRowBar[SC_SPLIT_BOTTOM]->GetEntryText(nRow); + const sal_uInt16 nSize = pDoc->GetRowHeight(nRow, aViewData.GetTabNo()); + const long nSizePixels = ScViewData::ToPixel(nSize, aViewData.GetPPTY()); + const OUString aText = pRowBar[SC_SPLIT_BOTTOM]->GetEntryText(nRow); bool bSkip = false; if (!rRectangle.IsEmpty()) @@ -2334,23 +2339,27 @@ OUString ScTabView::getRowColumnHeaders(const Rectangle& rRectangle) } if (!bSkip) { - boost::property_tree::ptree aRow; - aRow.put("size", OString::number((nTotalPixels + nSizePixels) / aViewData.GetPPTY()).getStr()); - aRow.put("text", aText.toUtf8().getStr()); - aRows.push_back(std::make_pair("", aRow)); + if (!bFirstRow) + aBuffer.append(", "); + + aBuffer.append("{ \"text\": \"").append(aText).append("\", "); + aBuffer.append("\"size\": \"").append(OUString::number((nTotalPixels + nSizePixels) / aViewData.GetPPTY())).append("\" }"); + bFirstRow = false; } nTotal += nSize; nTotalPixels += nSizePixels; } - boost::property_tree::ptree aCols; + aBuffer.append("],\n\"columns\":\n["); + nTotal = 0; nTotalPixels = 0; + bFirstRow = true; for (SCCOL nCol = 0; nCol <= nEndCol; ++nCol) { - sal_uInt16 nSize = pDoc->GetColWidth(nCol, aViewData.GetTabNo()); - long nSizePixels = ScViewData::ToPixel(nSize, aViewData.GetPPTX()); - OUString aText = pColBar[SC_SPLIT_LEFT]->GetEntryText(nCol); + const sal_uInt16 nSize = pDoc->GetColWidth(nCol, aViewData.GetTabNo()); + const long nSizePixels = ScViewData::ToPixel(nSize, aViewData.GetPPTX()); + const OUString aText = pColBar[SC_SPLIT_LEFT]->GetEntryText(nCol); bool bSkip = false; if (!rRectangle.IsEmpty()) @@ -2363,22 +2372,19 @@ OUString ScTabView::getRowColumnHeaders(const Rectangle& rRectangle) } if (!bSkip) { - boost::property_tree::ptree aCol; - aCol.put("size", OString::number((nTotalPixels + nSizePixels) / aViewData.GetPPTX()).getStr()); - aCol.put("text", aText.toUtf8().getStr()); - aCols.push_back(std::make_pair("", aCol)); + if (!bFirstRow) + aBuffer.append(", "); + + aBuffer.append("{ \"text\": \"").append(aText).append("\", "); + aBuffer.append("\"size\": \"").append(OUString::number((nTotalPixels + nSizePixels) / aViewData.GetPPTX())).append("\" }"); + bFirstRow = false; } nTotal += nSize; nTotalPixels += nSizePixels; } - boost::property_tree::ptree aTree; - aTree.put("commandName", ".uno:ViewRowColumnHeaders"); - aTree.add_child("rows", aRows); - aTree.add_child("columns", aCols); - std::stringstream aStream; - boost::property_tree::write_json(aStream, aTree); - return OUString::fromUtf8(aStream.str().c_str()); + aBuffer.append("]\n}"); + return aBuffer.makeStringAndClear(); } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |