135 lines
5.6 KiB
Java
135 lines
5.6 KiB
Java
/* ====================================================================
|
|
Licensed to the Apache Software Foundation (ASF) under one or more
|
|
contributor license agreements. See the NOTICE file distributed with
|
|
this work for additional information regarding copyright ownership.
|
|
The ASF licenses this file to You under the Apache License, Version 2.0
|
|
(the "License"); you may not use this file except in compliance with
|
|
the License. You may obtain a copy of the License at
|
|
|
|
http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
Unless required by applicable law or agreed to in writing, software
|
|
distributed under the License is distributed on an "AS IS" BASIS,
|
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
See the License for the specific language governing permissions and
|
|
limitations under the License.
|
|
==================================================================== */
|
|
|
|
package org.apache.poi.ss.formula.functions;
|
|
|
|
import org.apache.poi.hssf.HSSFTestDataSamples;
|
|
import org.apache.poi.hssf.usermodel.HSSFCell;
|
|
import org.apache.poi.hssf.usermodel.HSSFFormulaEvaluator;
|
|
import org.apache.poi.hssf.usermodel.HSSFRow;
|
|
import org.apache.poi.hssf.usermodel.HSSFSheet;
|
|
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
|
|
import org.apache.poi.ss.usermodel.CellType;
|
|
import org.apache.poi.ss.usermodel.CellValue;
|
|
|
|
import junit.framework.AssertionFailedError;
|
|
import junit.framework.TestCase;
|
|
|
|
/**
|
|
* Tests for {@link Irr}
|
|
*
|
|
* @author Marcel May
|
|
*/
|
|
public final class TestIrr extends TestCase {
|
|
|
|
public void testIrr() {
|
|
// http://en.wikipedia.org/wiki/Internal_rate_of_return#Example
|
|
double[] incomes = {-4000d, 1200d, 1410d, 1875d, 1050d};
|
|
double irr = Irr.irr(incomes);
|
|
double irrRounded = Math.round(irr * 1000d) / 1000d;
|
|
assertEquals("irr", 0.143d, irrRounded);
|
|
|
|
// http://www.techonthenet.com/excel/formulas/irr.php
|
|
incomes = new double[]{-7500d, 3000d, 5000d, 1200d, 4000d};
|
|
irr = Irr.irr(incomes);
|
|
irrRounded = Math.round(irr * 100d) / 100d;
|
|
assertEquals("irr", 0.28d, irrRounded);
|
|
|
|
incomes = new double[]{-10000d, 3400d, 6500d, 1000d};
|
|
irr = Irr.irr(incomes);
|
|
irrRounded = Math.round(irr * 100d) / 100d;
|
|
assertEquals("irr", 0.05, irrRounded);
|
|
|
|
incomes = new double[]{100d, -10d, -110d};
|
|
irr = Irr.irr(incomes);
|
|
irrRounded = Math.round(irr * 100d) / 100d;
|
|
assertEquals("irr", 0.1, irrRounded);
|
|
|
|
incomes = new double[]{-70000d, 12000, 15000};
|
|
irr = Irr.irr(incomes, -0.1);
|
|
irrRounded = Math.round(irr * 100d) / 100d;
|
|
assertEquals("irr", -0.44, irrRounded);
|
|
}
|
|
|
|
public void testEvaluateInSheet() {
|
|
HSSFWorkbook wb = new HSSFWorkbook();
|
|
HSSFSheet sheet = wb.createSheet("Sheet1");
|
|
HSSFRow row = sheet.createRow(0);
|
|
|
|
row.createCell(0).setCellValue(-4000d);
|
|
row.createCell(1).setCellValue(1200d);
|
|
row.createCell(2).setCellValue(1410d);
|
|
row.createCell(3).setCellValue(1875d);
|
|
row.createCell(4).setCellValue(1050d);
|
|
|
|
HSSFCell cell = row.createCell(5);
|
|
cell.setCellFormula("IRR(A1:E1)");
|
|
|
|
HSSFFormulaEvaluator fe = new HSSFFormulaEvaluator(wb);
|
|
fe.clearAllCachedResultValues();
|
|
fe.evaluateFormulaCellEnum(cell);
|
|
double res = cell.getNumericCellValue();
|
|
assertEquals(0.143d, Math.round(res * 1000d) / 1000d);
|
|
}
|
|
|
|
public void testIrrFromSpreadsheet(){
|
|
HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("IrrNpvTestCaseData.xls");
|
|
HSSFSheet sheet = wb.getSheet("IRR-NPV");
|
|
HSSFFormulaEvaluator fe = new HSSFFormulaEvaluator(wb);
|
|
StringBuffer failures = new StringBuffer();
|
|
int failureCount = 0;
|
|
// TODO YK: Formulas in rows 16 and 17 operate with ArrayPtg which isn't yet supported
|
|
// FormulaEvaluator as of r1041407 throws "Unexpected ptg class (org.apache.poi.ss.formula.ptg.ArrayPtg)"
|
|
for(int rownum = 9; rownum <= 15; rownum++){
|
|
HSSFRow row = sheet.getRow(rownum);
|
|
HSSFCell cellA = row.getCell(0);
|
|
try {
|
|
CellValue cv = fe.evaluate(cellA);
|
|
assertFormulaResult(cv, cellA);
|
|
} catch (Throwable e){
|
|
if(failures.length() > 0) failures.append('\n');
|
|
failures.append("Row[" + (cellA.getRowIndex() + 1)+ "]: " + cellA.getCellFormula() + " ");
|
|
failures.append(e.getMessage());
|
|
failureCount++;
|
|
}
|
|
|
|
HSSFCell cellC = row.getCell(2); //IRR-NPV relationship: NPV(IRR(values), values) = 0
|
|
try {
|
|
CellValue cv = fe.evaluate(cellC);
|
|
assertEquals(0, cv.getNumberValue(), 0.0001); // should agree within 0.01%
|
|
} catch (Throwable e){
|
|
if(failures.length() > 0) failures.append('\n');
|
|
failures.append("Row[" + (cellC.getRowIndex() + 1)+ "]: " + cellC.getCellFormula() + " ");
|
|
failures.append(e.getMessage());
|
|
failureCount++;
|
|
}
|
|
}
|
|
|
|
if(failures.length() > 0) {
|
|
throw new AssertionFailedError(failureCount + " IRR assertions failed:\n" + failures.toString());
|
|
}
|
|
|
|
}
|
|
|
|
private static void assertFormulaResult(CellValue cv, HSSFCell cell){
|
|
double actualValue = cv.getNumberValue();
|
|
double expectedValue = cell.getNumericCellValue(); // cached formula result calculated by Excel
|
|
assertEquals("Invalid formula result: " + cv.toString(), CellType.NUMERIC, cv.getCellTypeEnum());
|
|
assertEquals(expectedValue, actualValue, 1E-4); // should agree within 0.01%
|
|
}
|
|
}
|