final CMSStrikeIntegrant integrant = new CMSStrikeIntegrant(cmsCapFloor, sabrPoint, forward, _cutOffStrike, _mu);
final double factor = discountFactor * integrant.g(forward) / integrant.h(forward);
final double absoluteTolerance = 1.0E-9;
final double relativeTolerance = 1.0E-5;
final RungeKuttaIntegrator1D integrator = new RungeKuttaIntegrator1D(absoluteTolerance, relativeTolerance, getNbIteration());
final SABRExtrapolationRightFunction sabrExtrapolation = new SABRExtrapolationRightFunction(forward, sabrPoint, _cutOffStrike, cmsCapFloor.getFixingTime(), _mu);
final EuropeanVanillaOption option = new EuropeanVanillaOption(strike, cmsCapFloor.getFixingTime(), cmsCapFloor.isCap());
final double[] kpkpp = integrant.kpkpp(strike);
double firstPart;
double thirdPart;
if (cmsCapFloor.isCap()) {
firstPart = -kpkpp[0] * integrant.bs(strike);
thirdPart = integrator.integrate(integrant, strike, strike + getIntegrationInterval());
} else {
firstPart = 3 * kpkpp[0] * integrant.bs(strike);
thirdPart = integrator.integrate(integrant, 0.0, strike);
}
final double secondPart = integrant.k(strike) * sabrExtrapolation.priceDerivativeStrike(option);
return cmsCapFloor.getNotional() * cmsCapFloor.getPaymentYearFraction() * factor * (firstPart + secondPart + thirdPart);
}