DayCounter ComponentMust::eff_convert_basis(std::string basis) const { //cette fonction fait la conversion //de la convention de calcul (basis) de type string lue de XML de MUST // daycounter; if (basis == "A360") return Actual360(); if (basis == "A365") return Actual365Fixed(); if (basis == "Actual") return ActualActual(); if (basis == "Daily Price") return OneDayCounter(); if (basis == "Business 252") return Business252(); if (basis == "JGB") return Actual365NoLeap(); if (basis == "30/360") return Thirty360(Thirty360::EurobondBasis); return Thirty360(); }
USDLiborCurve(string tenor, Frequency fixedFrequency=Semiannual): CurveBase(boost::shared_ptr<IborIndex>(new USDLibor( Tenor(tenor) )), 2, fixedFrequency, ModifiedFollowing, Thirty360(Thirty360::European), ActualActual(ActualActual::ISDA) ) {}
USDLiborCurve(): CurveBase(boost::shared_ptr<IborIndex>(new USDLibor(Period(3,Months))), 2, Semiannual, ModifiedFollowing, Thirty360(Thirty360::European), ActualActual(ActualActual::ISDA) ) {}
BMAIndex::BMAIndex(const Handle<YieldTermStructure>& h) : InterestRateIndex("BMA", 1 * Weeks, 1, USDCurrency(), UnitedStates(UnitedStates::NYSE), ActualActual(ActualActual::ISDA)), termStructure_(h) { registerWith (h); }
JpyLiborSwapIsdaFixPm::JpyLiborSwapIsdaFixPm( const Period& tenor, const Handle<YieldTermStructure>& h) : SwapIndex("JpyLiborSwapIsdaFixPm", // familyName tenor, 2, // settlementDays JPYCurrency(), TARGET(), 6*Months, // fixedLegTenor ModifiedFollowing, // fixedLegConvention ActualActual(ActualActual::ISDA), // fixedLegDaycounter boost::shared_ptr<IborIndex>(new JPYLibor(6*Months, h))) {}
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void MonteCarloCDOEngine1::defaultScenarios() const { results_.expectedTrancheLoss.clear(); const vector<Date>& dates = arguments_.schedule.dates(); Date today = Settings::instance().evaluationDate(); Real tmax = ActualActual().yearFraction(today, dates.back()); QL_REQUIRE(tmax >= 0, "tmax < 0"); /* 1) Generate a vector of random default times in the single-factor Gaussian Copula framework 2) Work out cumulative portfolio and tranche loss for each scenario 3) Map cumulative tranche losses to schedule dates 4) Average over many scenarios */ const boost::shared_ptr<Pool> pool = remainingBasket_->pool(); vector<vector<Real> > cumulativeTrancheLoss(samples_, vector<Real>()); results_.expectedTrancheLoss.resize(dates.size(), 0.0); for (Size i = 0; i < samples_; i++) { rdm_->nextSequence(tmax); cumulativeTrancheLoss[i].resize(dates.size(), 0.0); remainingBasket_->updateScenarioLoss(); for (Size k = 0; k < dates.size(); k++) { cumulativeTrancheLoss[i][k] = remainingBasket_->scenarioTrancheLoss(dates[k]); // aggregate results_.expectedTrancheLoss[k] += cumulativeTrancheLoss[i][k]; } } // normalize for (Size i = 0; i < dates.size(); i++) results_.expectedTrancheLoss[i] /= samples_; }
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void MonteCarloCDOEngine2::calculate() const { Date today = Settings::instance().evaluationDate(); results_.protectionValue = 0.0; results_.premiumValue = 0.0; results_.expectedTrancheLoss.clear(); // set remainingBasket_, results_.remainingNotional, initialize(); const vector<Date>& dates = arguments_.schedule.dates(); if (dates.front() > today) results_.upfrontPremiumValue = arguments_.upfrontRate * results_.remainingNotional; Real tmax = ActualActual().yearFraction(today, dates.back()); //Real tmin = ActualActual().yearFraction(today, dates.front()); QL_REQUIRE(tmax >= 0, "tmax < 0"); vector<boost::shared_ptr<CashFlow> > premiumLeg = FixedRateLeg(arguments_.schedule) .withNotionals(1.0) .withCouponRates(arguments_.runningRate, arguments_.dayCounter) .withPaymentAdjustment(arguments_.paymentConvention); boost::shared_ptr<Pool> pool = remainingBasket_->pool(); vector<Real> premiumValue(samples_, 0.0); vector<Real> protectionValue(samples_, 0.0); vector<Real> value(samples_, 0.0); vector<Real> fairPremium(samples_, 0.0); vector<vector<Real> > cumulativeTrancheLoss(samples_, vector<Real>()); for (Size i = 0; i < samples_; i++) { //================================ /****************************************************************** * (1) Compute default times ******************************************************************/ rdm_->nextSequence(tmax); /****************************************************************** * (2) Cumulative tranche loss to schedule dates ******************************************************************/ cumulativeTrancheLoss[i].resize(dates.size(), 0.0); remainingBasket_->updateScenarioLoss(); for (Size k = 0; k < dates.size(); k++) cumulativeTrancheLoss[i][k] = remainingBasket_->scenarioTrancheLoss(dates[k]); /***************************************************************** * (3) Contribution of this scenario to the protection leg * - Loop through all incremental tranche loss events between * start and end date * - Pay and discount these increments as they occur *****************************************************************/ vector<Loss> increments = remainingBasket_->scenarioIncrementalTrancheLosses(dates.front(), dates.back()); for (Size k = 0; k < increments.size(); k++) protectionValue[i] += increments[k].amount * arguments_.yieldTS->discount(increments[k].time); /***************************************************************** * (4) Contribution of this scenario to the premium leg * - Loop through all coupon periods * - Pay coupon at period end on effective notional * - Effective notional: * - Start with remaining notional minus cumulative loss * on the tranche until period start =: N * - Reduce N for each loss in the period by subtracting the * the incremental tranche loss weighted with the time * to period end *****************************************************************/ for (Size j = 0; j < premiumLeg.size(); j++) { boost::shared_ptr<Coupon> coupon = boost::dynamic_pointer_cast<Coupon>(premiumLeg[j]); Date startDate = std::max(coupon->accrualStartDate(), arguments_.yieldTS->referenceDate()); Date endDate = coupon->accrualEndDate(); Date paymentDate = coupon->date(); if (paymentDate <= today) continue; Real t1 = ActualActual().yearFraction(today, startDate); Real t2 = ActualActual().yearFraction(today, endDate); Real PL = cumulativeTrancheLoss[i][j]; Real N = results_.remainingNotional - PL; for (Size k = 0; k < increments.size(); k++) { Real t = increments[k].time; if (t <= t1) continue; if (t >= t2) break; N -= (t2-t) / (t2-t1) * increments[k].amount; } Real discount = arguments_.yieldTS->discount(paymentDate); premiumValue[i] += N * coupon->amount() * discount; } /***************** * Aggregate *****************/ results_.premiumValue += premiumValue[i]; results_.protectionValue += protectionValue[i]; value[i] = premiumValue[i] - protectionValue[i] + results_.upfrontPremiumValue; for (Size k = 0; k < dates.size(); k++) results_.expectedTrancheLoss[k] += cumulativeTrancheLoss[i][k]; /* cout.setf (ios::fixed, ios::floatfield); cout << setprecision(0); for (Size k = 0; k < dates.size(); k++) cout << setw(3) << cumulativeTrancheLoss[i][k] << " "; cout << endl; cout << setprecision(2); for (Size k = 0; k < pool->size(); k++) { const string name = pool->names()[k]; Real t = pool->getTime(name); if (t < 6) cout << setw(10) << name << " " << setw(5) << t << endl; } */ } // end of loop over samples ========================================== /***************************************** * Expected values, normalize, switch sign *****************************************/ results_.premiumValue /= samples_; results_.protectionValue /= samples_; for (Size k = 0; k < dates.size(); k++) results_.expectedTrancheLoss[k] /= samples_; if (arguments_.side == Protection::Buyer) { results_.protectionValue *= -1; results_.premiumValue *= -1; results_.upfrontPremiumValue *= -1; } results_.value = results_.premiumValue - results_.protectionValue + results_.upfrontPremiumValue; /************************************************* * Error estimates - NPV *************************************************/ Real avg = 0.0; Real var = 0.0; for (Size i = 0; i < samples_; i++) { var += value[i] * value[i]; avg += value[i]; } avg /= samples_; var /= samples_; results_.errorEstimate = sqrt(var - avg * avg); /***************************************************** * Error estimates - fair premium * http://math.nyu.edu/~atm262/files/spring06/ircm/cdo *****************************************************/ /* Real x = 0.0, xx = 0.0, y = 0.0, yy = 0.0, xy = 0.0; for (Size i = 0; i < samples_; i++) { Real dx = protectionValue[i] - results_.upfrontPremiumValue; Real dy = premiumValue[i]; x += dx; xx += dx * dx; y += dy; yy += dy * dy; xy += dx * dy; } x /= samples_; y /= samples_; xx /= samples_; yy /= samples_; xy /= samples_; Real v = x*x/(y*y) * (xx/(x*x) + yy/(y*y) - 2.0 * xy/(x*y)); Real stdFairPremium = sqrt(v) * arguments_.runningRate; */ }
void americanSwaption( boost::shared_ptr<LiborForwardModel> & lfm, boost::shared_ptr<IborIndex> & libor, utilities::csvBuilder & file) { Date pricingDate = // pricing date Settings::instance().evaluationDate(); Date optionStart = libor->fixingCalendar().advance( // start in 2 days pricingDate, Period(2, Days)); Date optionEnd(16, July, 2016); Date fwdMaturity(16, July, 2021); //Date optionEnd = libor->fixingCalendar().advance( // start in 2 days // optionStart, // Period(6, Months)); //Date fwdMaturity = optionStart + Period(3, Years); // underlying 3 years Schedule schedule( optionStart, fwdMaturity, libor->tenor(), libor->fixingCalendar(), ModifiedFollowing, ModifiedFollowing, DateGeneration::Backward, false); Rate swapRate = 0.0404; // dummy swap rate boost::shared_ptr<VanillaSwap> forwardSwap( new VanillaSwap(VanillaSwap::Receiver, 100.0, schedule, swapRate, ActualActual(), schedule, libor, 0.0, libor->dayCounter())); forwardSwap->setPricingEngine(boost::shared_ptr<PricingEngine>( new DiscountingSwapEngine(libor->forwardingTermStructure()))); swapRate = forwardSwap->fairRate(); // obtain the fair rate forwardSwap = boost::shared_ptr<VanillaSwap>( // rebuild the "right" swap new VanillaSwap(VanillaSwap::Receiver, 100.0, schedule, swapRate, ActualActual(), schedule, libor, 0.0, libor->dayCounter())); forwardSwap->setPricingEngine(boost::shared_ptr<PricingEngine>( new DiscountingSwapEngine(libor->forwardingTermStructure()))); boost::shared_ptr<PricingEngine> engine( new LfmSwaptionEngine(lfm, libor->forwardingTermStructure())); boost::shared_ptr<Exercise> exercise( new AmericanExercise(optionEnd)); boost::shared_ptr<Swaption> americanSwaption( // create the swaption new Swaption(forwardSwap, exercise)); americanSwaption->setPricingEngine(engine); Real npv = americanSwaption->NPV(); std::cout << "American swaption npv: " // information << npv << std::endl; }