aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorYegor Kozlov <yegor@apache.org>2010-05-24 05:31:48 +0000
committerYegor Kozlov <yegor@apache.org>2010-05-24 05:31:48 +0000
commit9f0cd544cf702c31cbcbc0ea944a22b38784f213 (patch)
tree7109c8928cca2b7d927c3dc5c6f7b5d2b197a635 /src
parente79cc21802e5204a508d177aa3ff5d1331101b46 (diff)
downloadpoi-9f0cd544cf702c31cbcbc0ea944a22b38784f213.tar.gz
poi-9f0cd544cf702c31cbcbc0ea944a22b38784f213.zip
Improved performance of XSSFSheet.write, avoid unnecessary re-ordering of CTRow beans if they are already ordered
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@947542 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'src')
-rw-r--r--src/documentation/content/xdocs/status.xml1
-rw-r--r--src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java63
2 files changed, 44 insertions, 20 deletions
diff --git a/src/documentation/content/xdocs/status.xml b/src/documentation/content/xdocs/status.xml
index bb66430073..102f6cb529 100644
--- a/src/documentation/content/xdocs/status.xml
+++ b/src/documentation/content/xdocs/status.xml
@@ -34,6 +34,7 @@
<changes>
<release version="3.7-SNAPSHOT" date="2010-??-??">
+ <action dev="POI-DEVELOPERS" type="add">Improved performance of XSSFWorkbook.write </action>
<action dev="POI-DEVELOPERS" type="fix">48846 - Avoid NPE when finding cell comments</action>
<action dev="POI-DEVELOPERS" type="fix">49325 - Ensure that CTPhoneticPr is included in poi-ooxml jar</action>
<action dev="POI-DEVELOPERS" type="fix">49191 - Fixed tests failing in non-english locales</action>
diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java
index 14fcd81f3b..4600553690 100644
--- a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java
+++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java
@@ -113,7 +113,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
protected CTSheet sheet;
protected CTWorksheet worksheet;
- private TreeMap<Integer, XSSFRow> rows;
+ private TreeMap<Integer, XSSFRow> _rows;
private List<XSSFHyperlink> hyperlinks;
private ColumnHelper columnHelper;
private CommentsTable sheetComments;
@@ -194,12 +194,12 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
}
private void initRows(CTWorksheet worksheet) {
- rows = new TreeMap<Integer, XSSFRow>();
+ _rows = new TreeMap<Integer, XSSFRow>();
sharedFormulas = new HashMap<Integer, XSSFCell>();
arrayFormulas = new ArrayList<CellRangeAddress>();
for (CTRow row : worksheet.getSheetData().getRowArray()) {
XSSFRow r = new XSSFRow(row, this);
- rows.put(r.getRowNum(), r);
+ _rows.put(r.getRowNum(), r);
}
}
@@ -503,7 +503,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
*/
public XSSFRow createRow(int rownum) {
CTRow ctRow;
- XSSFRow prev = rows.get(rownum);
+ XSSFRow prev = _rows.get(rownum);
if(prev != null){
ctRow = prev.getCTRow();
ctRow.set(CTRow.Factory.newInstance());
@@ -512,7 +512,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
}
XSSFRow r = new XSSFRow(ctRow, this);
r.setRowNum(rownum);
- rows.put(rownum, r);
+ _rows.put(rownum, r);
return r;
}
@@ -707,7 +707,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
* @return the number of the first logical row on the sheet, zero based
*/
public int getFirstRowNum() {
- return rows.size() == 0 ? 0 : rows.firstKey();
+ return _rows.size() == 0 ? 0 : _rows.firstKey();
}
/**
@@ -820,7 +820,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
}
public int getLastRowNum() {
- return rows.size() == 0 ? 0 : rows.lastKey();
+ return _rows.size() == 0 ? 0 : _rows.lastKey();
}
public short getLeftCol() {
@@ -948,7 +948,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
* @return the number of phsyically defined rows
*/
public int getPhysicalNumberOfRows() {
- return rows.size();
+ return _rows.size();
}
/**
@@ -977,7 +977,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
* @return <code>XSSFRow</code> representing the rownumber or <code>null</code> if its not defined on the sheet
*/
public XSSFRow getRow(int rownum) {
- return rows.get(rownum);
+ return _rows.get(rownum);
}
/**
@@ -1158,7 +1158,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
private short getMaxOutlineLevelRows(){
short outlineLevel=0;
- for(XSSFRow xrow : rows.values()){
+ for(XSSFRow xrow : _rows.values()){
outlineLevel=xrow.getCTRow().getOutlineLevel()>outlineLevel? xrow.getCTRow().getOutlineLevel(): outlineLevel;
}
return outlineLevel;
@@ -1358,7 +1358,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
xcell.notifyArrayFormulaChanging(msg);
}
}
- rows.remove(row.getRowNum());
+ _rows.remove(row.getRowNum());
}
/**
@@ -1380,7 +1380,7 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
* Call getRowNum() on each row if you care which one it is.
*/
public Iterator<Row> rowIterator() {
- return (Iterator<Row>)(Iterator<? extends Row>)rows.values().iterator();
+ return (Iterator<Row>)(Iterator<? extends Row>) _rows.values().iterator();
}
/**
@@ -2157,12 +2157,12 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
rowShifter.updateFormulas(shifter);
rowShifter.shiftMerged(startRow, endRow, n);
- //rebuild the rows map
+ //rebuild the _rows map
TreeMap<Integer, XSSFRow> map = new TreeMap<Integer, XSSFRow>();
- for(XSSFRow r : rows.values()) {
+ for(XSSFRow r : _rows.values()) {
map.put(r.getRowNum(), r);
}
- rows = map;
+ _rows = map;
}
/**
@@ -2441,13 +2441,10 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
worksheet.getHyperlinks().setHyperlinkArray(ctHls);
}
- CTSheetData sheetData = worksheet.getSheetData();
- ArrayList<CTRow> rArray = new ArrayList<CTRow>(rows.size());
- for(XSSFRow row : rows.values()){
+ for(XSSFRow row : _rows.values()){
row.onDocumentWrite();
- rArray.add(row.getCTRow());
}
- sheetData.setRowArray(rArray.toArray(new CTRow[rArray.size()]));
+ ensureRowOrdering();
XmlOptions xmlOptions = new XmlOptions(DEFAULT_XML_OPTIONS);
xmlOptions.setSaveSyntheticDocumentElement(new QName(CTWorksheet.type.getName().getNamespaceURI(), "worksheet"));
@@ -2459,6 +2456,32 @@ public class XSSFSheet extends POIXMLDocumentPart implements Sheet {
}
/**
+ * ensure that the array of CTRow written to CTSheetData is ordered by row index
+ */
+ private void ensureRowOrdering(){
+ CTSheetData sheetData = worksheet.getSheetData();
+ // check if row indexes in CTSheetData match the internal model:
+ // rows in the internal model (_rows) are always ordered while
+ // CTRow beans held by CTSheetData may be not, for example, user can
+ // insert rows in random order, shift rows after insertion, etc.
+ Integer [] curRows = new Integer[sheetData.sizeOfRowArray()];
+ int i = 0;
+ for(CTRow ctrow : sheetData.getRowArray()){
+ curRows[i++] = (int)(ctrow.getR() - 1);
+ }
+ Integer [] ordRows = _rows.keySet().toArray(new Integer[_rows.size()]);
+ if(!Arrays.equals(curRows, ordRows)){
+ // The order of rows in CTSheetData and internal model does not match
+ CTRow[] orderedCTRows = new CTRow[_rows.size()];
+ i = 0;
+ for(XSSFRow row : _rows.values()){
+ orderedCTRows[i++] = row.getCTRow();
+ }
+ sheetData.setRowArray(orderedCTRows);
+ }
+ }
+
+ /**
* @return true when Autofilters are locked and the sheet is protected.
*/
public boolean isAutoFilterLocked() {