Files
ARM64/MarketData/MarketDataLib/Generator/TermStructure/TermStructureGenerator.cs
2025-03-25 21:42:32 -04:00

139 lines
5.9 KiB
C#
Executable File

using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Configuration;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using MarketData.Numerical;
using MarketData.DataAccess;
using MarketData.MarketDataModel;
using MarketData.Utils;
namespace MarketData.Generator.TermStructure
{
public class TermStructureInterpolatorByDate : Dictionary<DateTime,TermStructureInterpolator>
{
}
public class TermStructureInterpolator
{
private Dictionary<int, double> splineRates = new Dictionary<int, double>();
private CurveData curveData = null;
private DateTime tradeDate;
public TermStructureInterpolator(DateTime tradeDate)
{
this.tradeDate=tradeDate;
SetCurveData();
}
public DateTime TradeDate { get; private set; }
public CurveData CurveData
{
get
{
return curveData;
}
}
public Dictionary<int, double> SplineRates
{
get
{
return splineRates;
}
}
public double GetRate(int days)
{
int index = 0;
if (null == curveData) return double.NaN;
for (; index < curveData.CurveTenors.Count;index++ )
{
Tenor tenor = curveData.CurveTenors[index];
int tenorDays=Tenor.GetTenorDays(tenor.Item);
if(tenorDays == days) return double.Parse(tenor.Value);
if(tenorDays>days) break;
}
double differenceDays=days-Tenor.GetTenorDays(curveData.CurveTenors[index].Item);
double dailyRate=(curveData.CurveTenors[index].ValueNum - curveData.CurveTenors[index-1].ValueNum) / (curveData.CurveTenors[index].Days - curveData.CurveTenors[index-1].Days);
double rate = curveData.CurveTenors[index].ValueNum + (differenceDays * dailyRate);
return rate;
}
private void SetCurveData()
{
YieldCurveData yieldCurveData=YieldCurveDA.GetYieldCurve(tradeDate);
if(null==yieldCurveData)return;
curveData=new CurveData();
Tenors tenors=new Tenors();
curveData.CurveTenors=tenors;
tenors.Add(new Tenor("1D",Utility.FormatNumber(yieldCurveData.Mo1,2)));
tenors.Add(new Tenor("1M",Utility.FormatNumber(yieldCurveData.Mo1,2)));
tenors.Add(new Tenor("3M",Utility.FormatNumber(yieldCurveData.Mo3,2)));
tenors.Add(new Tenor("6M",Utility.FormatNumber(yieldCurveData.Mo6,2)));
tenors.Add(new Tenor("1Y",Utility.FormatNumber(yieldCurveData.Yr1,2)));
tenors.Add(new Tenor("2Y",Utility.FormatNumber(yieldCurveData.Yr2,2)));
tenors.Add(new Tenor("3Y",Utility.FormatNumber(yieldCurveData.Yr3,2)));
tenors.Add(new Tenor("5Y",Utility.FormatNumber(yieldCurveData.Yr5,2)));
tenors.Add(new Tenor("7Y",Utility.FormatNumber(yieldCurveData.Yr7,2)));
tenors.Add(new Tenor("10Y",Utility.FormatNumber(yieldCurveData.Yr10,2)));
tenors.Add(new Tenor("20Y",Utility.FormatNumber(yieldCurveData.Yr20,2)));
tenors.Add(new Tenor("30Y",Utility.FormatNumber(yieldCurveData.Yr30,2)));
List<Element> sourcePairs = new List<Element>();
List<Element> destPairs = new List<Element>();
sourcePairs.Add(new Element(0,double.Parse(curveData.GetTenorValue("1D"))));
sourcePairs.Add(new Element(30,double.Parse(curveData.GetTenorValue("1M"))));
sourcePairs.Add(new Element(90,double.Parse(curveData.GetTenorValue("3M"))));
sourcePairs.Add(new Element(180,double.Parse(curveData.GetTenorValue("6M"))));
sourcePairs.Add(new Element(360,double.Parse(curveData.GetTenorValue("1Y"))));
sourcePairs.Add(new Element(720,double.Parse(curveData.GetTenorValue("2Y"))));
sourcePairs.Add(new Element(1080,double.Parse(curveData.GetTenorValue("3Y"))));
sourcePairs.Add(new Element(1800,double.Parse(curveData.GetTenorValue("5Y"))));
sourcePairs.Add(new Element(2520,double.Parse(curveData.GetTenorValue("7Y"))));
sourcePairs.Add(new Element(3600,double.Parse(curveData.GetTenorValue("10Y"))));
sourcePairs.Add(new Element(7200,double.Parse(curveData.GetTenorValue("20Y"))));
sourcePairs.Add(new Element(10800,double.Parse(curveData.GetTenorValue("30Y"))));
for (int index = 0; index <= 10800; index++)destPairs.Add(new Element(index, 0));
Element[] sourcePairsArray = sourcePairs.ToArray();
Element[] destPairsArray = destPairs.ToArray();
CatmullRom.PerformSpline(sourcePairsArray,destPairsArray);
for (int index = 0; index < destPairsArray.Length; index++)
{
if (!splineRates.ContainsKey((int)destPairsArray[index].Column))
{
splineRates.Add((int)destPairsArray[index].Column, destPairsArray[index].Row);
}
}
}
}
// *************************************************************************************************************************************************************
public class TermStructureRatesGenerator
{
private TermStructureInterpolatorByDate termStructureInterpolatorByDate = new TermStructureInterpolatorByDate();
public TermStructureRatesGenerator()
{
}
public void Add(DateTime tradeDate)
{
if (termStructureInterpolatorByDate.ContainsKey(tradeDate)) return;
termStructureInterpolatorByDate.Add(tradeDate,new TermStructureInterpolator(tradeDate));
}
public CurveData GetTermStructureCurve(DateTime tradeDate)
{
if (null == termStructureInterpolatorByDate||!termStructureInterpolatorByDate.ContainsKey(tradeDate)) return null;
TermStructureInterpolator termStructureInterpolator = termStructureInterpolatorByDate[tradeDate];
return termStructureInterpolator.CurveData;
}
public double GetRate(DateTime tradeDate,int days)
{
if (!termStructureInterpolatorByDate.ContainsKey(tradeDate)) return double.NaN;
TermStructureInterpolator termStructureInterpolator = termStructureInterpolatorByDate[tradeDate];
return termStructureInterpolator.GetRate(days);
}
}
}