1 /* -*- mode: c++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 2 3 /* 4 Copyright (C) 2011 Klaus Spanderen 5 6 This file is part of QuantLib, a free-software/open-source library 7 for financial quantitative analysts and developers - http://quantlib.org/ 8 9 QuantLib is free software: you can redistribute it and/or modify it 10 under the terms of the QuantLib license. You should have received a 11 copy of the license along with this program; if not, please email 12 <quantlib-dev@lists.sf.net>. The license is also available online at 13 <http://quantlib.org/license.shtml>. 14 15 This program is distributed in the hope that it will be useful, but WITHOUT 16 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 17 FOR A PARTICULAR PURPOSE. See the license for more details. 18 */ 19 20 /*! \file fdoujumpvanillaengine.cpp 21 \brief Finite Differences Ornstein Uhlenbeck plus exponential jumps engine 22 for simple swing options 23 */ 24 25 #include <ql/exercise.hpp> 26 #include <ql/termstructures/yieldtermstructure.hpp> 27 #include <ql/experimental/processes/extouwithjumpsprocess.hpp> 28 #include <ql/experimental/processes/extendedornsteinuhlenbeckprocess.hpp> 29 #include <ql/methods/finitedifferences/operators/fdmlinearoplayout.hpp> 30 #include <ql/methods/finitedifferences/meshers/fdmmeshercomposite.hpp> 31 #include <ql/experimental/finitedifferences/fdmextoujumpmodelinnervalue.hpp> 32 #include <ql/methods/finitedifferences/stepconditions/fdmamericanstepcondition.hpp> 33 #include <ql/methods/finitedifferences/stepconditions/fdmbermudanstepcondition.hpp> 34 #include <ql/methods/finitedifferences/stepconditions/fdmstepconditioncomposite.hpp> 35 #include <ql/methods/finitedifferences/meshers/exponentialjump1dmesher.hpp> 36 #include <ql/experimental/finitedifferences/fdmextoujumpsolver.hpp> 37 #include <ql/methods/finitedifferences/meshers/fdmsimpleprocess1dmesher.hpp> 38 #include <ql/experimental/finitedifferences/fdextoujumpvanillaengine.hpp> 39 40 namespace QuantLib { 41 FdExtOUJumpVanillaEngine(const ext::shared_ptr<ExtOUWithJumpsProcess> & process,const ext::shared_ptr<YieldTermStructure> & rTS,Size tGrid,Size xGrid,Size yGrid,const ext::shared_ptr<Shape> & shape,const FdmSchemeDesc & schemeDesc)42 FdExtOUJumpVanillaEngine::FdExtOUJumpVanillaEngine( 43 const ext::shared_ptr<ExtOUWithJumpsProcess>& process, 44 const ext::shared_ptr<YieldTermStructure>& rTS, 45 Size tGrid, Size xGrid, Size yGrid, 46 const ext::shared_ptr<Shape>& shape, 47 const FdmSchemeDesc& schemeDesc) 48 : process_(process), 49 rTS_(rTS), 50 shape_(shape), 51 tGrid_(tGrid), 52 xGrid_(xGrid), 53 yGrid_(yGrid), 54 schemeDesc_(schemeDesc) { 55 } 56 calculate() const57 void FdExtOUJumpVanillaEngine::calculate() const { 58 // 1. Mesher 59 const Time maturity 60 = rTS_->dayCounter().yearFraction(rTS_->referenceDate(), 61 arguments_.exercise->lastDate()); 62 const ext::shared_ptr<StochasticProcess1D> ouProcess( 63 process_->getExtendedOrnsteinUhlenbeckProcess()); 64 const ext::shared_ptr<Fdm1dMesher> xMesher( 65 new FdmSimpleProcess1dMesher(xGrid_, ouProcess,maturity)); 66 67 const ext::shared_ptr<Fdm1dMesher> yMesher( 68 new ExponentialJump1dMesher(yGrid_, 69 process_->beta(), 70 process_->jumpIntensity(), 71 process_->eta())); 72 73 const ext::shared_ptr<FdmMesher> mesher( 74 new FdmMesherComposite(xMesher, yMesher)); 75 76 // 2. Calculator 77 const ext::shared_ptr<FdmInnerValueCalculator> calculator( 78 new FdmExtOUJumpModelInnerValue(arguments_.payoff, mesher, shape_)); 79 80 // 3. Step conditions 81 const ext::shared_ptr<FdmStepConditionComposite> conditions = 82 FdmStepConditionComposite::vanillaComposite( 83 DividendSchedule(), arguments_.exercise, 84 mesher, calculator, 85 rTS_->referenceDate(), rTS_->dayCounter()); 86 87 // 4. Boundary conditions 88 const FdmBoundaryConditionSet boundaries; 89 90 // 5. set-up solver 91 FdmSolverDesc solverDesc = { mesher, boundaries, conditions, 92 calculator, maturity, tGrid_, 0 }; 93 94 const ext::shared_ptr<FdmExtOUJumpSolver> solver( 95 new FdmExtOUJumpSolver(Handle<ExtOUWithJumpsProcess>(process_), 96 rTS_, solverDesc, schemeDesc_)); 97 98 const Real x = process_->initialValues()[0]; 99 const Real y = process_->initialValues()[1]; 100 results_.value = solver->valueAt(x, y); 101 } 102 } 103