Esempio n. 1
0
        public BlackFuturesCurve(IATMVolSurface volSurface, DateTime startDate, DateTime expiryDate, int nTimeSteps, Func <DateTime, double> forwardCurve, string name, IFutureSettingsProvider futureSettingsProvider, Dictionary <DateTime, double> pastFixings = null)
        {
            _surface                = volSurface;
            _startDate              = startDate;
            _expiryDate             = expiryDate;
            _numberOfSteps          = nTimeSteps;
            _name                   = name;
            _forwardCurve           = forwardCurve;
            _pastFixings            = pastFixings ?? (new Dictionary <DateTime, double>());
            _futureSettingsProvider = futureSettingsProvider;
            if (startDate > expiryDate)
            {
                throw new Exception("Start date must be before expiry date");
            }
            _codes           = new List <string>();
            _futuresExpiries = new List <DateTime>();
            var fCode       = new FutureCode(name, _futureSettingsProvider);
            var currentCode = fCode.GetFrontMonth(startDate);

            _codes.Add(currentCode);
            fCode = new FutureCode(currentCode, DateTime.Today.Year - 2, _futureSettingsProvider);
            _futuresExpiries.Add(fCode.GetRollDate());
            fCode = new FutureCode(currentCode, DateTime.Today.Year - 2, _futureSettingsProvider);
            var targetCode = fCode.GetFrontMonth(expiryDate);

            while (currentCode != targetCode)
            {
                currentCode = fCode.GetNextCode(false);
                _futuresExpiries.Add(fCode.GetRollDate());
                _codes.Add(currentCode);
            }
        }
Esempio n. 2
0
        public FutureCode(string futureCode, int yearBeforeWhich2DigitDatesAreUsed, IFutureSettingsProvider futureSettings)
        {
            OriginalCode = futureCode;
            YearBeforeWhich2DigitDatesAreUsed = yearBeforeWhich2DigitDatesAreUsed;
            _futureSettingsProvider           = futureSettings;

            //Find the last number
            var i = 0;
            int tempNumber;

            for (i = futureCode.Length; i >= 0; i--)
            {
                if (int.TryParse(futureCode[i - 1].ToString(), out tempNumber))
                {
                    break;
                }
            }

            //Now we have the index we can hack the end off
            Postfix    = futureCode.Substring(i);
            futureCode = futureCode.Substring(0, i);

            //Find when the numbers end

            for (i = futureCode.Length; i >= 0; i--)
            {
                if (!int.TryParse(futureCode[i - 1].ToString(), out tempNumber))
                {
                    break;
                }
            }

            YearCode        = futureCode.Substring(i);
            YearNumber      = int.Parse(YearCode);
            YearNumberShort = YearNumber;

            futureCode = futureCode.Substring(0, i);

            MonthCode = futureCode[futureCode.Length - 1].ToString();
            Prefix    = futureCode.Substring(0, futureCode.Length - 1);

            if (!futureSettings.TryGet(Prefix, out _settings))
            {
                ContractCode = Prefix.ToUpper().Trim();
                _settings    = futureSettings[ContractCode];
            }

            MonthNumber12 = s_futureMonths.ToList().IndexOf(MonthCode) + 1;
            MonthNumber   = _settings.Months.IndexOf(MonthCode) + 1;
            ConvertYearCode();
        }
Esempio n. 3
0
        public static RiskyFlySurface GetSurfaceForCode(string nymexSymbol, string nymexOptionFilename, string qwackCode, BasicPriceCurve priceCurve, ICalendarProvider calendarProvider, ICurrencyProvider currency, IFutureSettingsProvider futureSettingsProvider)
        {
            var parsed = NYMEXOptionParser.Instance.Parse(nymexOptionFilename).Where(r => r.Symbol == nymexSymbol);

            var(optionExerciseType, optionMarginingType) = OptionTypeFromCode(nymexSymbol);
            var origin = DateTime.ParseExact(parsed.First().TradeDate, "MM/dd/yyyy", CultureInfo.InvariantCulture);

            var q = parsed.Where(x => x.Settle > 0).Select(x => new ListedOptionSettlementRecord
            {
                CallPut               = x.PutCall == "C"?OptionType.C:OptionType.P,
                ExerciseType          = optionExerciseType,
                MarginType            = optionMarginingType,
                PV                    = x.Settle,
                Strike                = x.Strike,
                UnderlyingFuturesCode = Year2to1(x.Contract.Split(' ')[0].Replace(nymexSymbol, qwackCode)),
                ExpiryDate            = OptionExpiryFromNymexRecord(x, calendarProvider),
                ValDate               = origin
            }).Where(z => z.ExpiryDate > origin).ToList();

            var priceDict = priceCurve.PillarLabels.ToDictionary(x => x, x => priceCurve.GetPriceForDate(priceCurve.PillarDatesForLabel(x)));

            ListedSurfaceHelper.ImplyVols(q, priceDict, new ConstantRateIrCurve(0.0, origin, "dummy", currency.GetCurrency("USD")));
            var smiles = ListedSurfaceHelper.ToDeltaSmiles(q, priceDict);

            var allOptionExpiries = new List <DateTime>();
            var lastDate          = q.Max(x => x.ExpiryDate);

            var dummyFutureCode = $"{qwackCode}Z{DateExtensions.SingleDigitYear(DateTime.Today.Year + 2)}";
            var c = new FutureCode(dummyFutureCode, DateTime.Today.Year - 2, futureSettingsProvider);

            var contract     = c.GetFrontMonth(origin, false);
            var lastContract = c.GetFrontMonth(lastDate, false);

            while (contract != lastContract)
            {
                var cc     = new FutureCode(contract, origin.Year, futureSettingsProvider);
                var exp    = ListedUtils.FuturesCodeToDateTime(contract);
                var record = new NYMEXOptionRecord
                {
                    ContractMonth = exp.Month,
                    ContractYear  = exp.Year,
                    Symbol        = nymexSymbol
                };
                var optExpiry = OptionExpiryFromNymexRecord(record, calendarProvider);
                if (optExpiry > origin)
                {
                    allOptionExpiries.Add(optExpiry);
                }

                contract = cc.GetNextCode(false);
            }

            var surface = ListedSurfaceHelper.ToRiskyFlySurfaceStepFlat(smiles, origin, priceCurve, allOptionExpiries, currency);

            return(surface);
        }
Esempio n. 4
0
        public static BasicPriceCurve GetCurveForCode(string nymexSymbol, string nymexFutureFilename, string qwackCode, IFutureSettingsProvider provider, ICurrencyProvider currency)
        {
            var parsed    = NYMEXFutureParser.Instance.Parse(nymexFutureFilename).Where(r => r.Symbol == nymexSymbol);
            var q         = parsed.Where(x => x.Settle.HasValue).ToDictionary(x => Year2to1(x.Contract.Replace(nymexSymbol, qwackCode)), x => x.Settle);
            var datesDict = q.ToDictionary(x => FutureCode.GetExpiryFromCode(x.Key, provider), x => x.Key);
            var datesVec  = datesDict.Keys.OrderBy(x => x).ToArray();
            var labelsVec = datesVec.Select(d => datesDict[d]).ToArray();
            var pricesVec = labelsVec.Select(l => System.Math.Max(q[l].Value, MinPrice)).ToArray();
            var origin    = DateTime.ParseExact(parsed.First().TradeDate, "MM/dd/yyyy", CultureInfo.InvariantCulture);
            var curve     = new BasicPriceCurve(origin, datesVec, pricesVec, PriceCurveType.NYMEX, currency, labelsVec)
            {
                AssetId = qwackCode,
                Name    = qwackCode,
                SpotLag = 0.Bd()
            };

            return(curve);
        }
Esempio n. 5
0
        private static IFundingInstrument ToQwackIns(this CMEFileRecord record, string qwackCode, IFutureSettingsProvider futureSettingsProvider, ICurrencyProvider currencyProvider, Dictionary <string, FloatRateIndex> indices, Dictionary <string, string> forecastCurves)
        {
            switch (qwackCode)
            {
            case "ED":
                var edExp = FutureCode.GetExpiryFromCode(MmmYtoCode(record.MMY, qwackCode), futureSettingsProvider);
                return(new STIRFuture
                {
                    ContractSize = 1e6,
                    Currency = currencyProvider.GetCurrency("USD"),
                    DCF = 0.25,
                    ConvexityAdjustment = 0,
                    Price = record.SettlePrice.Value,
                    Index = indices["ED"],
                    Expiry = edExp,
                    PillarDate = edExp.AddMonths(3),
                    TradeId = qwackCode + record.MMY,
                    Position = 1,
                    SolveCurve = forecastCurves["ED"],
                    ForecastCurve = forecastCurves["ED"],
                });

            case "FF":
                var ffEnd   = FutureCode.GetExpiryFromCode(MmmYtoCode(record.MMY, qwackCode), futureSettingsProvider);
                var ffStart = ffEnd.FirstDayOfMonth();
                return(new OISFuture
                {
                    ContractSize = 1e6,
                    Currency = currencyProvider.GetCurrency("USD"),
                    DCF = ffStart.CalculateYearFraction(ffEnd, DayCountBasis.ACT360),
                    Price = record.SettlePrice.Value,
                    Index = indices["FF"],
                    PillarDate = ffEnd,
                    TradeId = qwackCode + record.MMY,
                    Position = 1,
                    SolveCurve = forecastCurves["FF"],
                    ForecastCurve = forecastCurves["FF"],
                    AverageStartDate = ffStart,
                    AverageEndDate = ffEnd,
                });

            default:
                throw new Exception($"No mapping found for code {qwackCode}");
            }
        }
Esempio n. 6
0
        public static IrCurve GetCurveForCode(string cmeId, string cmeFilename, string qwackCode, string curveName, Dictionary <string, FloatRateIndex> indices, Dictionary <string, string> curves, IFutureSettingsProvider futureSettingsProvider, ICurrencyProvider currencyProvider, ICalendarProvider calendarProvider)
        {
            var parsed      = CMEFileParser.Parse(cmeFilename).Where(r => r.ID == cmeId && r.SecTyp == "FUT");
            var q           = parsed.ToDictionary(x => DateTime.ParseExact(x.MatDt, "yyyy-MM-dd", CultureInfo.InvariantCulture), x => x.SettlePrice);
            var origin      = DateTime.ParseExact(parsed.First().BizDt, "yyyy-MM-dd", CultureInfo.InvariantCulture);
            var instruments = parsed.Select(p => ToQwackIns(p, qwackCode, futureSettingsProvider, currencyProvider, indices, curves)).ToList();
            var pillars     = instruments.Select(x => x.PillarDate).OrderBy(x => x).ToArray();
            var fic         = new FundingInstrumentCollection(currencyProvider);

            fic.AddRange(instruments);
            var curve = new IrCurve(pillars, pillars.Select(p => 0.01).ToArray(), origin, curveName, Interpolator1DType.Linear, currencyProvider.GetCurrency("USD"));
            var fm    = new FundingModel(origin, new[] { curve }, currencyProvider, calendarProvider);

            var solver = new NewtonRaphsonMultiCurveSolverStaged();

            solver.Solve(fm, fic);
            return(curve);
        }
Esempio n. 7
0
        public AssetFxMCModel(DateTime originDate, Portfolio portfolio, IAssetFxModel model, McSettings settings, ICurrencyProvider currencyProvider, IFutureSettingsProvider futureSettingsProvider, ICalendarProvider calendarProvider)
        {
            if (settings.CompactMemoryMode && settings.AveragePathCorrection)
            {
                throw new Exception("Can't use both CompactMemoryMode and PathCorrection");
            }

            _currencyProvider       = currencyProvider;
            _futureSettingsProvider = futureSettingsProvider;
            _calendarProvider       = calendarProvider;
            Engine = new PathEngine(settings.NumberOfPaths)
            {
                Parallelize       = settings.Parallelize,
                CompactMemoryMode = settings.CompactMemoryMode
            };
            OriginDate = originDate;
            Portfolio  = portfolio;
            Model      = model;
            Settings   = settings;
            switch (settings.Generator)
            {
            case RandomGeneratorType.MersenneTwister:
                Engine.AddPathProcess(new Random.MersenneTwister.MersenneTwister64()
                {
                    UseNormalInverse = true,
                    UseAnthithetic   = false
                });
                break;

            case RandomGeneratorType.Sobol:
                var directionNumers = new Random.Sobol.SobolDirectionNumbers(GetSobolFilename());
                Engine.AddPathProcess(new Random.Sobol.SobolPathGenerator(directionNumers, 1000)
                {
                    UseNormalInverse = true
                });
                break;

            case RandomGeneratorType.Constant:
                Engine.AddPathProcess(new Random.Constant.Constant()
                {
                    UseNormalInverse = true,
                });
                break;

            case RandomGeneratorType.FlipFlop:
                Engine.AddPathProcess(new Random.Constant.FlipFlop(settings.CreditSettings.ConfidenceInterval, true));
                break;
            }
            Engine.IncrementDepth();

            if (model.CorrelationMatrix != null)
            {
                if (settings.LocalCorrelation)
                {
                    Engine.AddPathProcess(new CholeskyWithTime(model.CorrelationMatrix, model));
                }
                else
                {
                    Engine.AddPathProcess(new Cholesky(model.CorrelationMatrix));
                }
                Engine.IncrementDepth();
            }

            var lastDate         = portfolio.LastSensitivityDate;
            var assetIds         = portfolio.AssetIds();
            var assetInstruments = portfolio.Instruments
                                   .Where(x => x is IAssetInstrument)
                                   .Select(x => x as IAssetInstrument);
            var fixingsNeeded = new Dictionary <string, List <DateTime> >();

            foreach (var ins in assetInstruments)
            {
                var fixingsForIns = ins.PastFixingDates(originDate);
                if (fixingsForIns.Any())
                {
                    foreach (var kv in fixingsForIns)
                    {
                        if (!fixingsNeeded.ContainsKey(kv.Key))
                        {
                            fixingsNeeded.Add(kv.Key, new List <DateTime>());
                        }
                        fixingsNeeded[kv.Key] = fixingsNeeded[kv.Key].Concat(kv.Value).Distinct().ToList();
                    }
                }
            }

            //asset processes
            var fxAssetsToAdd = new List <string>();
            var corrections   = new Dictionary <string, SimpleAveragePathCorrector>();

            foreach (var assetId in assetIds)
            {
                if (assetId.Length == 7 && assetId[3] == '/')
                {
                    fxAssetsToAdd.Add(assetId);
                    continue;
                }

                if (!(model.GetVolSurface(assetId) is IATMVolSurface surface))
                {
                    throw new Exception($"Vol surface for asset {assetId} could not be cast to IATMVolSurface");
                }
                var fixingDict = fixingsNeeded.ContainsKey(assetId) ? model.GetFixingDictionary(assetId) : null;
                var fixings    = fixingDict != null ?
                                 fixingsNeeded[assetId].ToDictionary(x => x, x => fixingDict.GetFixing(x))
                    : new Dictionary <DateTime, double>();
                var futuresSim = settings.ExpensiveFuturesSimulation &&
                                 (model.GetPriceCurve(assetId).CurveType == PriceCurveType.ICE || model.GetPriceCurve(assetId).CurveType == PriceCurveType.NYMEX);
                if (futuresSim)
                {
                    var fwdCurve = new Func <DateTime, double>(t =>
                    {
                        return(model.GetPriceCurve(assetId).GetPriceForDate(t));
                    });
                    var asset = new BlackFuturesCurve
                                (
                        startDate: originDate,
                        expiryDate: lastDate,
                        volSurface: surface,
                        forwardCurve: fwdCurve,
                        nTimeSteps: settings.NumberOfTimesteps,
                        name: Settings.FuturesMappingTable[assetId],
                        pastFixings: fixings,
                        futureSettingsProvider: _futureSettingsProvider
                                );
                    Engine.AddPathProcess(asset);
                }
                else
                {
                    var fwdCurve = new Func <double, double>(t =>
                    {
                        var c = model.GetPriceCurve(assetId);
                        var d = originDate.AddYearFraction(t, DayCountBasis.ACT365F);
                        if (c is PriceCurve pc)
                        {
                            d = d.AddPeriod(RollType.F, pc.SpotCalendar, pc.SpotLag);
                        }
                        else if (c is ContangoPriceCurve cc)
                        {
                            d = d.AddPeriod(RollType.F, cc.SpotCalendar, cc.SpotLag);
                        }
                        return(c.GetPriceForDate(d));
                    });

                    IATMVolSurface adjSurface  = null;
                    var            correlation = 0.0;

                    if (settings.ReportingCurrency != model.GetPriceCurve(assetId).Currency)
                    {
                        var fxAdjPair    = settings.ReportingCurrency + "/" + model.GetPriceCurve(assetId).Currency;
                        var fxAdjPairInv = model.GetPriceCurve(assetId).Currency + "/" + settings.ReportingCurrency;
                        if (!(model.FundingModel.GetVolSurface(fxAdjPair) is IATMVolSurface adjSurface2))
                        {
                            throw new Exception($"Vol surface for fx pair {fxAdjPair} could not be cast to IATMVolSurface");
                        }
                        adjSurface = adjSurface2;
                        if (model.CorrelationMatrix != null)
                        {
                            if (model.CorrelationMatrix.TryGetCorrelation(fxAdjPair, assetId, out var correl))
                            {
                                correlation = correl;
                            }
                            else if (model.CorrelationMatrix.TryGetCorrelation(fxAdjPairInv, assetId, out var correl2))
                            {
                                correlation = -correl2;
                            }
                        }
                    }

                    if (settings.McModelType == McModelType.LocalVol)
                    {
                        var asset = new LVSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: assetId,
                            pastFixings: fixings,
                            fxAdjustSurface: adjSurface,
                            fxAssetCorrelation: correlation
                                    );
                        Engine.AddPathProcess(asset);
                    }
                    else if (settings.McModelType == McModelType.TurboSkew)
                    {
                        var asset = new TurboSkewSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: assetId,
                            pastFixings: fixings,
                            fxAdjustSurface: adjSurface,
                            fxAssetCorrelation: correlation
                                    );
                        Engine.AddPathProcess(asset);
                    }
                    else
                    {
                        var asset = new BlackSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: assetId,
                            pastFixings: fixings,
                            fxAdjustSurface: adjSurface,
                            fxAssetCorrelation: correlation
                                    );
                        Engine.AddPathProcess(asset);
                    }
                    if (settings.AveragePathCorrection)
                    {
                        corrections.Add(assetId, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(assetId)
                        {
                            CompactMode = settings.CompactMemoryMode
                        }, surface, fwdCurve, assetId, fixings, adjSurface, correlation));
                    }
                }
            }

            //fx pairs
            var pairsAdded = new List <string>();
            var fxPairs    = portfolio.FxPairs(model).Concat(fxAssetsToAdd);
            var payoutCcys = portfolio.Instruments.Select(i => i.Currency);

            if (payoutCcys.Any(p => p != settings.ReportingCurrency))
            {
                var ccysToAdd  = payoutCcys.Where(p => p != settings.ReportingCurrency).Distinct();
                var pairsToAdd = ccysToAdd.Select(c => $"{c.Ccy}/{settings.ReportingCurrency}");
                fxPairs = fxPairs.Concat(pairsToAdd).Distinct();
            }
            foreach (var fxPair in fxPairs)
            {
                var fxPairName = fxPair;
                var pair       = fxPairName.FxPairFromString(_currencyProvider, _calendarProvider);

                if (pairsAdded.Contains(pair.ToString()))
                {
                    continue;
                }

                if (!(model.FundingModel.VolSurfaces[fxPairName] is IATMVolSurface surface))
                {
                    throw new Exception($"Vol surface for fx pair {fxPairName} could not be cast to IATMVolSurface");
                }

                var fwdCurve = new Func <double, double>(t =>
                {
                    var date     = originDate.AddYearFraction(t, DayCountBasis.ACT365F);
                    var spotDate = pair.SpotDate(date);
                    return(model.FundingModel.GetFxRate(spotDate, fxPairName));
                });

                pairsAdded.Add(pair.ToString());

                if (settings.McModelType == McModelType.LocalVol)
                {
                    var asset = new LVSingleAsset
                                (
                        startDate: originDate,
                        expiryDate: lastDate,
                        volSurface: surface,
                        forwardCurve: fwdCurve,
                        nTimeSteps: settings.NumberOfTimesteps,
                        name: fxPairName
                                );
                    Engine.AddPathProcess(asset);

                    if (settings.AveragePathCorrection)
                    {
                        corrections.Add(fxPairName, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(fxPairName)
                        {
                            CompactMode = settings.CompactMemoryMode
                        }, surface, fwdCurve, fxPairName));
                    }
                }
                else if (settings.McModelType == McModelType.TurboSkew)
                {
                    if (fxPairName.Substring(fxPairName.Length - 3, 3) != settings.ReportingCurrency)
                    {//needs to be drift-adjusted
                        var fxAdjPair = settings.ReportingCurrency + "/" + fxPairName.Substring(fxPairName.Length - 3, 3);
                        if (!(model.FundingModel.VolSurfaces[fxAdjPair] is IATMVolSurface adjSurface))
                        {
                            throw new Exception($"Vol surface for fx pair {fxAdjPair} could not be cast to IATMVolSurface");
                        }
                        var correlation = fxPair == fxAdjPair ? -1.0 : 0.0;
                        if (correlation != -1.0 && model.CorrelationMatrix != null)
                        {
                            if (model.CorrelationMatrix.TryGetCorrelation(fxAdjPair, fxPair, out var correl))
                            {
                                correlation = correl;
                            }
                        }

                        var asset = new TurboSkewSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: fxPairName,
                            fxAdjustSurface: adjSurface,
                            fxAssetCorrelation: correlation
                                    );
                        Engine.AddPathProcess(asset);

                        if (settings.AveragePathCorrection)
                        {
                            corrections.Add(fxPairName, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(fxPairName)
                            {
                                CompactMode = settings.CompactMemoryMode
                            }, surface, fwdCurve, fxPairName, null, adjSurface, correlation));
                        }
                    }
                    else
                    {
                        var asset = new TurboSkewSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: fxPairName
                                    );
                        Engine.AddPathProcess(asset);

                        if (settings.AveragePathCorrection)
                        {
                            corrections.Add(fxPairName, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(fxPairName)
                            {
                                CompactMode = settings.CompactMemoryMode
                            }, surface, fwdCurve, fxPairName));
                        }
                    }
                }
                else
                {
                    if (fxPairName.Substring(fxPairName.Length - 3, 3) != settings.ReportingCurrency)
                    {//needs to be drift-adjusted
                        var fxAdjPair = settings.ReportingCurrency + "/" + fxPairName.Substring(fxPairName.Length - 3, 3);
                        if (!(model.FundingModel.VolSurfaces[fxAdjPair] is IATMVolSurface adjSurface))
                        {
                            throw new Exception($"Vol surface for fx pair {fxAdjPair} could not be cast to IATMVolSurface");
                        }
                        var correlation = fxPair == fxAdjPair ? -1.0 : 0.0;
                        if (correlation != -1.0 && model.CorrelationMatrix != null)
                        {
                            if (model.CorrelationMatrix.TryGetCorrelation(fxAdjPair, fxPair, out var correl))
                            {
                                correlation = correl;
                            }
                        }

                        var asset = new BlackSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: fxPairName,
                            fxAdjustSurface: adjSurface,
                            fxAssetCorrelation: correlation
                                    );
                        Engine.AddPathProcess(asset);

                        if (settings.AveragePathCorrection)
                        {
                            corrections.Add(fxPairName, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(fxPairName)
                            {
                                CompactMode = settings.CompactMemoryMode
                            }, surface, fwdCurve, fxPairName, null, adjSurface, correlation));
                        }
                    }
                    else
                    {
                        var asset = new BlackSingleAsset
                                    (
                            startDate: originDate,
                            expiryDate: lastDate,
                            volSurface: surface,
                            forwardCurve: fwdCurve,
                            nTimeSteps: settings.NumberOfTimesteps,
                            name: fxPairName
                                    );
                        Engine.AddPathProcess(asset);

                        if (settings.AveragePathCorrection)
                        {
                            corrections.Add(fxPairName, new SimpleAveragePathCorrector(new SimpleAveragePathCalculator(fxPairName)
                            {
                                CompactMode = settings.CompactMemoryMode
                            }, surface, fwdCurve, fxPairName));
                        }
                    }
                }
            }
            //apply path correctin
            if (settings.AveragePathCorrection && corrections.Any())
            {
                Engine.IncrementDepth();
                foreach (var pc in corrections)
                {
                    Engine.AddPathProcess(pc.Value.PathCalc);
                }
                Engine.IncrementDepth();
                foreach (var pc in corrections)
                {
                    Engine.AddPathProcess(pc.Value);
                }
            }

            //payoffs
            Engine.IncrementDepth();
            _payoffs = assetInstruments.ToDictionary(x => x.TradeId, y => new AssetPathPayoff(y, _currencyProvider, _calendarProvider, settings.ReportingCurrency));
            if (!settings.AvoidRegressionForBackPricing && _payoffs.Any(x => x.Value.Regressors != null))
            {
                var regressorsToAdd = _payoffs.Where(x => x.Value.Regressors != null)
                                      .SelectMany(x => x.Value.Regressors)
                                      .Distinct();

                foreach (var regressor in regressorsToAdd)
                {
                    Engine.AddPathProcess(regressor);
                    foreach (var payoff in _payoffs.Where(x => x.Value.Regressors != null))
                    {
                        if (payoff.Value.Regressors.Any(x => x == regressor))
                        {
                            payoff.Value.SetRegressor(regressor);
                        }
                    }
                }

                Engine.IncrementDepth();
            }
            foreach (var product in _payoffs)
            {
                if (settings.AvoidRegressionForBackPricing && (product.Value.AssetInstrument is BackPricingOption || product.Value.AssetInstrument is MultiPeriodBackpricingOption))
                {
                    product.Value.VanillaModel = VanillaModel;
                }

                Engine.AddPathProcess(product.Value);
            }

            var metricsNeedRegression = new[] { BaseMetric.PFE, BaseMetric.KVA, BaseMetric.CVA, BaseMetric.FVA, BaseMetric.EPE };

            //Need to calculate PFE
            if (settings.CreditSettings != null && settings.CreditSettings.ExposureDates != null && settings.ReportingCurrency != null && metricsNeedRegression.Contains(settings.CreditSettings.Metric))//setup for PFE, etc
            {
                Engine.IncrementDepth();

                switch (settings.CreditSettings.PfeRegressorType)
                {
                case PFERegressorType.MultiLinear:
                    _regressor = new LinearPortfolioValueRegressor(settings.CreditSettings.ExposureDates,
                                                                   _payoffs.Values.ToArray(), settings);
                    break;

                case PFERegressorType.MonoLinear:
                    _regressor = new MonoIndexRegressor(settings.CreditSettings.ExposureDates,
                                                        _payoffs.Values.ToArray(), settings, true);
                    break;
                }
                Engine.AddPathProcess(_regressor);
            }

            //Need to calculate expected capital
            if (settings.CreditSettings != null && settings.CreditSettings.ExposureDates != null && settings.ReportingCurrency != null && settings.CreditSettings.Metric == BaseMetric.ExpectedCapital)
            {
                Engine.IncrementDepth();
                _capitalCalc = new ExpectedCapitalCalculator(Portfolio, settings.CreditSettings.CounterpartyRiskWeighting, settings.CreditSettings.AssetIdToHedgeGroupMap, settings.ReportingCurrency, VanillaModel, settings.CreditSettings.ExposureDates);
                Engine.AddPathProcess(_capitalCalc);
            }

            Engine.SetupFeatures();
        }
Esempio n. 8
0
        public AssetFxModel BuildModel(DateTime valDate, ModelBuilderSpec spec, IFutureSettingsProvider futureSettingsProvider, ICurrencyProvider currencyProvider, ICalendarProvider calendarProvider)
        {
            var indices     = spec.RateIndices.ToDictionary(x => x.Key, x => new FloatRateIndex(x.Value, calendarProvider, currencyProvider));
            var fxPairs     = spec.FxPairs.Select(x => new FxPair(x, currencyProvider, calendarProvider)).ToList();
            var priceCurves = new List <IPriceCurve>();
            var surfaces    = new List <IVolSurface>();
            var fxSurfaces  = new List <IVolSurface>();

            foreach (var c in spec.NymexSpecs)
            {
                var curve = NYMEXModelBuilder.GetCurveForCode(c.NymexCodeFuture, Path.Combine(_filepath, FilenameNymexFuture), c.QwackCode, futureSettingsProvider, currencyProvider);
                priceCurves.Add(curve);
                if (!string.IsNullOrWhiteSpace(c.NymexCodeOption))
                {
                    var surface = NYMEXModelBuilder.GetSurfaceForCode(c.NymexCodeOption, Path.Combine(_filepath, FilenameNymexOption), c.QwackCode, curve, calendarProvider, currencyProvider, futureSettingsProvider);
                    surface.AssetId = c.QwackCode;
                    surfaces.Add(surface);
                }
            }
            var irCurves = new Dictionary <string, IrCurve>();

            foreach (var c in spec.CmeBaseCurveSpecs)
            {
                var ixForThis = new Dictionary <string, FloatRateIndex> {
                    { c.QwackCode, indices[c.FloatRateIndex] }
                };
                var curve = CMEModelBuilder.GetCurveForCode(c.CmeCode, Path.Combine(_filepath, c.IsCbot? FilenameCbot:FilenameCme), c.QwackCode, c.CurveName, ixForThis,
                                                            new Dictionary <string, string>()
                {
                    { c.QwackCode, c.CurveName }
                }, futureSettingsProvider, currencyProvider, calendarProvider);
                irCurves.Add(c.CurveName, curve);
            }
            foreach (var c in spec.CmeBasisCurveSpecs)
            {
                var fxPair = fxPairs.Single(x => $"{x.Domestic}{x.Foreign}" == c.FxPair);
                var curve  = CMEModelBuilder.StripFxBasisCurve(Path.Combine(_filepath, FilenameCmeFwdsXml), fxPair, c.CmeFxPair, currencyProvider.GetCurrency(c.Currency), c.CurveName, valDate, irCurves[c.BaseCurveName], currencyProvider, calendarProvider);
                irCurves.Add(c.CurveName, curve);
            }
            foreach (var c in spec.CmeFxFutureSpecs)
            {
                var curve   = CMEModelBuilder.GetFuturesCurveForCode(c.CmeCodeFut, Path.Combine(_filepath, FilenameCme), currencyProvider);
                var surface = CMEModelBuilder.GetFxSurfaceForCode(c.CmeCodeOpt, Path.Combine(_filepath, FilenameCme), curve, currencyProvider);
                surface.AssetId = c.FxPair;
                fxSurfaces.Add(surface);
            }

            var pairMap     = spec.CmeBasisCurveSpecs.ToDictionary(x => x.FxPair, x => x.CmeFxPair);
            var pairCcyMap  = spec.CmeBasisCurveSpecs.ToDictionary(x => x.FxPair, x => currencyProvider.GetCurrency(x.Currency));
            var spotRates   = CMEModelBuilder.GetSpotFxRatesFromFwdFile(Path.Combine(_filepath, FilenameCmeFwdsXml), valDate, pairMap, currencyProvider, calendarProvider);
            var discountMap = spec.CmeBasisCurveSpecs.ToDictionary(x => pairCcyMap[x.FxPair], x => x.CurveName);

            foreach (var c in spec.CmxMetalCurves)
            {
                var fxPair = fxPairs.Single(x => $"{x.Domestic}{x.Foreign}" == c.MetalPair);
                var(curve, spotPrice) = COMEXModelBuilder.GetMetalCurveForCode(Path.Combine(_filepath, FilenameCmxFwdsXml), c.CmxSymbol, fxPair, c.CurveName, valDate, irCurves[c.BaseCurveName], currencyProvider, calendarProvider);
                irCurves.Add(c.CurveName, curve);
                spotRates.Add(c.MetalPair, spotPrice);
                discountMap.Add(currencyProvider.GetCurrency(c.Currency), c.CurveName);
                pairCcyMap.Add(c.MetalPair, currencyProvider.GetCurrency(c.Currency));
                if (!string.IsNullOrWhiteSpace(c.CmxOptCode))
                {
                    var surface = COMEXModelBuilder.GetMetalSurfaceForCode(c.CmxOptCode, Path.Combine(_filepath, FilenameCmxXml), currencyProvider);
                    surface.AssetId = c.MetalPair;
                    fxSurfaces.Add(surface);
                }
            }

            var fm = new FundingModel(valDate, irCurves, currencyProvider, calendarProvider);

            var spotRatesByCcy = spotRates.ToDictionary(x => pairCcyMap[x.Key], x => x.Key.StartsWith("USD") ? x.Value : 1.0 / x.Value);

            var fxMatrix = new FxMatrix(currencyProvider);

            fxMatrix.Init(
                baseCurrency: currencyProvider.GetCurrency("USD"),
                buildDate: valDate,
                spotRates: spotRatesByCcy,
                fXPairDefinitions: fxPairs,
                discountCurveMap: discountMap);
            fm.SetupFx(fxMatrix);
            foreach (var fxs in fxSurfaces)
            {
                fm.VolSurfaces.Add(fxs.AssetId, fxs);
            }
            var o = new AssetFxModel(valDate, fm);

            o.AddVolSurfaces(surfaces.ToDictionary(s => s.AssetId, s => s));
            o.AddPriceCurves(priceCurves.ToDictionary(c => c.AssetId, c => c));
            return(o);
        }
Esempio n. 9
0
 public FutureCode(string futureCodeRoot, IFutureSettingsProvider futureSettings)
 {
     _settings = futureSettings[futureCodeRoot];
     _futureSettingsProvider = futureSettings;
     Prefix = futureCodeRoot;
 }
Esempio n. 10
0
        public static DateTime GetRollFromCode(string code, IFutureSettingsProvider futureSettingsProvider)
        {
            var c = new FutureCode(code, DateTime.Today.Year - 2, futureSettingsProvider);

            return(c.GetRollDate());
        }