/** * Greeks against finite difference approximation. */ public void greekfdTest() { for (double strike : STRIKES) { // call testDerivatives(strike, true, BARRIER_UP_IN); testDerivatives(strike, true, BARRIER_UP_OUT); testDerivatives(strike, true, BARRIER_DOWN_IN); testDerivatives(strike, true, BARRIER_DOWN_OUT); // put testDerivatives(strike, false, BARRIER_UP_IN); testDerivatives(strike, false, BARRIER_UP_OUT); testDerivatives(strike, false, BARRIER_DOWN_IN); testDerivatives(strike, false, BARRIER_DOWN_OUT); } }
/** * smoothly connected to limiting cases. */ public void smallsigmaTTest() { for (double strike : STRIKES) { // call testSmallValues(strike, true, BARRIER_UP_IN); testSmallValues(strike, true, BARRIER_UP_OUT); testSmallValues(strike, true, BARRIER_DOWN_IN); testSmallValues(strike, true, BARRIER_DOWN_OUT); // put testSmallValues(strike, false, BARRIER_UP_IN); testSmallValues(strike, false, BARRIER_UP_OUT); testSmallValues(strike, false, BARRIER_DOWN_IN); testSmallValues(strike, false, BARRIER_DOWN_OUT); } }
/** * Upper barrier level is very high: knock-in is close to 0, knock-out is close to vanilla. */ public void largeBarrierTest() { SimpleConstantContinuousBarrier upIn = SimpleConstantContinuousBarrier.of(BarrierType.UP, KnockType.KNOCK_IN, 1.0e4); SimpleConstantContinuousBarrier upOut = SimpleConstantContinuousBarrier.of(BarrierType.UP, KnockType.KNOCK_OUT, 1.0e4); for (double strike : STRIKES) { // call double callVanilla = BlackFormulaRepository.price(FWD_FX, strike, EXPIRY_TIME, VOLATILITY, true) * DF_DOM; double callUpIn = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, true, upIn); double callUpOut = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, true, upOut); assertRelative(callUpIn, 0d); assertRelative(callUpOut, callVanilla); // put double putVanilla = BlackFormulaRepository.price(FWD_FX, strike, EXPIRY_TIME, VOLATILITY, false) * DF_DOM; double putUpIn = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, false, upIn); double putUpOut = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, false, upOut); assertRelative(putUpIn, 0d); assertRelative(putUpOut, putVanilla); } }
/** * Lower barrier level is very small: knock-in is close to 0, knock-out is close to vanilla. */ public void smallBarrierTest() { SimpleConstantContinuousBarrier dwIn = SimpleConstantContinuousBarrier.of(BarrierType.DOWN, KnockType.KNOCK_IN, 0.1d); SimpleConstantContinuousBarrier dwOut = SimpleConstantContinuousBarrier.of(BarrierType.DOWN, KnockType.KNOCK_OUT, 0.1d); for (double strike : STRIKES) { // call double callVanilla = BlackFormulaRepository.price(FWD_FX, strike, EXPIRY_TIME, VOLATILITY, true) * DF_DOM; double callDwIn = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, true, dwIn); double callDwOut = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, true, dwOut); assertRelative(callDwIn, 0d); assertRelative(callDwOut, callVanilla); // put double putVanilla = BlackFormulaRepository.price(FWD_FX, strike, EXPIRY_TIME, VOLATILITY, false) * DF_DOM; double putDwIn = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, false, dwIn); double putDwOut = BARRIER_PRICER.price(SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, false, dwOut); assertRelative(putDwIn, 0d); assertRelative(putDwOut, putVanilla); } }
private void testSmallValues(double strike, boolean isCall, SimpleConstantContinuousBarrier barrier) { // small parameters double volUp = 2.0e-3; double volDw = 1.0e-3; double time = 1.0e-2; // price double optUp = BARRIER_PRICER.price(SPOT, strike, time, COST_OF_CARRY, RATE_DOM, volUp, isCall, barrier); double optDw = BARRIER_PRICER.price(SPOT, strike, time, COST_OF_CARRY, RATE_DOM, volDw, isCall, barrier); assertRelative(optUp, optDw); // price adjoint ValueDerivatives optUpAdj = BARRIER_PRICER.priceAdjoint(SPOT, strike, time, COST_OF_CARRY, RATE_DOM, volUp, isCall, barrier); ValueDerivatives optDwAdj = BARRIER_PRICER.priceAdjoint(SPOT, strike, time, COST_OF_CARRY, RATE_DOM, volDw, isCall, barrier); assertRelative(optUpAdj.getValue(), optDwAdj.getValue()); for (int i = 0; i < 6; ++i) { assertRelative(optUpAdj.getDerivative(i), optDwAdj.getDerivative(i)); } }
double callDownOut = BARRIER_PRICER.price( SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, true, BARRIER_DOWN_OUT); assertRelative(callUpIn + callUpOut, callVanilla); assertRelative(callDownIn + callDownOut, callVanilla); double putDownOut = BARRIER_PRICER.price( SPOT, strike, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, false, BARRIER_DOWN_OUT); assertRelative(putUpIn + putUpOut, putVanilla); assertRelative(putDownIn + putDownOut, putVanilla);
ValueDerivatives priceDIAdjointRb = rebate.priceAdjoint(SPOT, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, BARRIER_DOWN_OUT); assertRelative(priceDIExp[j], priceDINew + priceDIRb * REBATE); assertRelative(priceDIExp[j], priceDIAdjointNew.getValue() + priceDIAdjointRb.getValue() * REBATE); ValueDerivatives priceDOAdjointRb = rebate.priceAdjoint( SPOT, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, BARRIER_DOWN_IN); assertRelative(priceDOExp[j], priceDONew + priceDORb * REBATE); assertRelative(priceDOExp[j], priceDOAdjointNew.getValue() + priceDOAdjointRb.getValue() * REBATE); ValueDerivatives priceUIAdjointRb = rebate.priceAdjoint(SPOT, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, BARRIER_UP_OUT); assertRelative(priceUIExp[j], priceUINew + priceUIRb * REBATE); assertRelative(priceUIExp[j], priceUIAdjointNew.getValue() + priceUIAdjointRb.getValue() * REBATE); ValueDerivatives priceUOAdjointRb = rebate.priceAdjoint(SPOT, EXPIRY_TIME, COST_OF_CARRY, RATE_DOM, VOLATILITY, BARRIER_UP_IN); assertRelative(priceUOExp[j], priceUONew + priceUORb * REBATE); assertRelative(priceUOExp[j], priceUOAdjointNew.getValue() + priceUOAdjointRb.getValue() * REBATE); double rebateUI = i == 1 ? 0d : priceUIAdjointRb.getDerivative(k); double rebateUO = i == 1 ? 0d : priceUOAdjointRb.getDerivative(k); assertRelative(derivativesDIExp[j][i], priceDIAdjointNew.getDerivative(i) + REBATE * rebateDI); assertRelative(derivativesDOExp[j][i], priceDOAdjointNew.getDerivative(i) + REBATE * rebateDO); assertRelative(derivativesUIExp[j][i], priceUIAdjointNew.getDerivative(i) + REBATE * rebateUI); assertRelative(derivativesUOExp[j][i], priceUOAdjointNew.getDerivative(i) + REBATE * rebateUO);