checkVols(capVols);
checkErrors(errors);
final MultiCapFloorPricer pricer = getPricer();
LeastSquareResults lsRes;
if (solveViaPrice) {
final double[] capPrices = pricer.price(capVols);
lsRes = solveForPrice(capPrices, capVols, errors, true);
} else {
final Function1D<DoubleMatrix1D, DoubleMatrix1D> modelVolFunc = new Function1D<DoubleMatrix1D, DoubleMatrix1D>() {
@SuppressWarnings("synthetic-access")
@Override
public DoubleMatrix1D evaluate(final DoubleMatrix1D x) {
final double[] modelVols = pricer.impliedVols(_volModel.evaluate(x));
return new DoubleMatrix1D(modelVols);
}
};
lsRes = NLLSWP.solve(new DoubleMatrix1D(capVols), new DoubleMatrix1D(errors), modelVolFunc, new DoubleMatrix1D(_nWeights, capVols[capVols.length - 1]), _penalty);
}
final VolatilityTermStructure volCurve = getVolCurve(lsRes.getFitParameters());
final double[] mVols = pricer.impliedVols(volCurve);
// least-squares gives chi2 including the penalty, and is calculated via the price differecne and vega w we just want the fit error
// TODO maybe the solver should provide this?
final double chi2 = chiSqr(capVols, mVols, errors);
return new CapletStrippingSingleStrikeResult(chi2, lsRes.getFitParameters(), volCurve, new DoubleMatrix1D(mVols));
}