Files
zszq-trs/YLErpDAL/QdpModule/MarketProxy.cs
T
2024-05-09 14:06:26 +08:00

240 lines
7.9 KiB
C#

using Qdp.ComputeService.Data.CommonModels.MarketInfos;
using Qdp.ComputeService.Data.CommonModels.MarketInfos.CurveDefinitions;
using Qdp.Foundation.Implementations;
using Qdp.Pricing.Base.Enums;
using Qdp.Pricing.Base.Implementations;
using Qdp.Pricing.Base.Interfaces;
using Qdp.Pricing.Base.Utilities;
using Qdp.Pricing.Ecosystem.Market;
using Qdp.Pricing.Ecosystem.Utilities;
using Qdp.Pricing.Library.Common.Market;
using YLErp.Abstract;
using YLErp.Commons;
namespace YLErp.QdpModule
{
/// <summary>
/// 非线程安全类
/// </summary>
public class MarketProxy : IDisposable
{
public const string ConstantZeroCurve = "ConstantZeroCurve";
public const string RiskFreeDiscountCurve = "RiskFreeDiscountCurve";
public MarketProxy(DateTime valueDate, double sysRiskFreeRate, string curveDayCount = null)
{
ValueDate = valueDate;
RiskFreeRate = sysRiskFreeRate;
QdpMarket = new PrebuiltQdpMarket(valueDate.ToString("yyyy-MM-dd"), valueDate);
SetYieldCurve(ConstantZeroCurve, QdpHelper.CreateRiskFreeCurve(ConstantZeroCurve, 0));
CurveDayCount = curveDayCount;
if (string.IsNullOrEmpty(CurveDayCount))
{
CurveDayCount = BLL.valuedateBLL.SystemDate.CurveDayCount;
}
SetYieldCurve(RiskFreeDiscountCurve, QdpHelper.CreateRiskFreeCurve(DiscountCurveName, RiskFreeRate, CurveDayCount));
}
#region----属性定义----
/// <summary>
/// 计算日期
/// </summary>
public DateTime ValueDate { get; private set; }
/// <summary>
/// QDP Market对象
/// </summary>
public PrebuiltQdpMarket QdpMarket { get; }
/// <summary>
/// 无风险利率
/// </summary>
public double RiskFreeRate { get; }
/// <summary>
/// 无风险利率曲线名称
/// </summary>
public string DiscountCurveName => RiskFreeDiscountCurve;
/// <summary>
/// 用于计算跟踪输出
/// </summary>
public TraceWrap Trace { get; set; }
/// <summary>
/// 曲面日历
/// </summary>
public string CurveDayCount { get; }
#endregion
#region----利率曲线/标的物价格/波动率/相关性----
/// <summary>
/// 添加利率曲线
/// </summary>
public void SetYieldCurve(string curveName, InstrumentCurveDefinition curveDefinition)
{
YieldCurve instrumentCurve = null;
if (curveDefinition.RateDefinitions.All(x => x.InstrumentType.ToInstrumentType() == InstrumentType.Dummy || x.InstrumentType.ToInstrumentType() == InstrumentType.None))
{
if (curveDefinition.RateDefinitions.All(x => x.IsTerm()))
{
instrumentCurve = new YieldCurve(
curveDefinition.Name,
ValueDate,
curveDefinition.RateDefinitions.Select(x => Tuple.Create((ITerm)new Term(x.Tenor), x.Rate)).ToArray(),
curveDefinition.CurveConvention.BusinessDayConvention.ToBda(),
curveDefinition.CurveConvention.DayCount.ToDayCountImpl(),
curveDefinition.CurveConvention.Calendar.ToCalendarImpl(),
curveDefinition.CurveConvention.Currency.ToCurrencyCode(),
curveDefinition.CurveConvention.Compound.ToCompound(),
curveDefinition.CurveConvention.Interpolation.ToInterpolation(),
curveDefinition.Trait.ToYieldCurveTrait()
);
}
else
{
instrumentCurve = new YieldCurve(
curveDefinition.Name,
ValueDate,
curveDefinition.RateDefinitions.Select(x => Tuple.Create(new Date(DateTime.Parse(x.Tenor)), x.Rate)).ToArray(),
curveDefinition.CurveConvention.BusinessDayConvention.ToBda(),
curveDefinition.CurveConvention.DayCount.ToDayCountImpl(),
curveDefinition.CurveConvention.Calendar.ToCalendarImpl(),
curveDefinition.CurveConvention.Currency.ToCurrencyCode(),
curveDefinition.CurveConvention.Compound.ToCompound(),
curveDefinition.CurveConvention.Interpolation.ToInterpolation(),
curveDefinition.Trait.ToYieldCurveTrait()
);
}
}
QdpMarket.YieldCurves[curveName] = instrumentCurve;
}
/// <summary>
/// 添加股票价格
/// </summary>
public void SetStockPrice(string ticker, double price)
{
QdpMarket.StockPrices[ticker] = price;
}
/// <summary>
/// 移除波动率曲面
/// </summary>
public bool RemoveYieldCurve(string curveName)
{
if (string.IsNullOrEmpty(curveName))
{
return false;
}
return QdpMarket.YieldCurves.Remove(curveName);
}
/// <summary>
/// 设置波动率
/// </summary>
public void SetVolSurface(string volSurfaceName, double consVol)
{
var volatility = QdpModule.QdpVolHelper.GenerateFlatSurface(consVol);
SetVolSurface(volSurfaceName, volatility);
}
/// <summary>
/// 设置波动率
/// </summary>
public void SetVolSurface(string volSurfaceName, IVolatility volatility, double addVolRate = 0, bool isAddVolPercent = true)
{
if (string.IsNullOrWhiteSpace(volSurfaceName))
{
throw new ArgumentNullException(nameof(volSurfaceName));
}
if (volatility is null)
{
throw new ArgumentNullException(nameof(volatility));
}
if (volatility.VolTable is null)
{
throw new ArgumentException("VolTable不能为null", nameof(volatility));
}
Trace?.WriteData(volatility, "波动率名称:" + volSurfaceName);
var wrap = new VolSurfaceBuilder
{
volSurfaceName = volSurfaceName,
volSurfaceType = volatility.VolSurfaceMode,
interpolation = volatility.InterpolationMethod
}.SetVectors(volatility.VolTable, addVolRate, isAddVolPercent).Build(ValueDate);
QdpMarket.VolSurfaces[wrap.VolSurfaceName] = wrap.VolSurface;
}
/// <summary>
/// 设置相关性
/// </summary>
public void SetCorrelation(string[] underlyingTickers, double correlation)
{
var corrName = underlyingTickers.Length > 1 ? (underlyingTickers[0] + "_" + underlyingTickers[1]) : underlyingTickers[0];
var corrSurface = new CorrSurfMktData(corrName, correlation);
QdpMarket.CorrSurfaces[corrName] = corrSurface.ToImpliedVolSurface(ValueDate);
}
#endregion
#region----请求自增ID----
int _requestId = 1;
/// <summary>
/// 获取下一个请求ID
/// </summary>
public int NextRequestId()
{
return _requestId++;
}
#endregion
#region----释放资源---
bool isDisposed;
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (isDisposed)
{
return;
}
if (disposing)
{
QdpMarket.Dispose();
}
isDisposed = true;
}
#endregion
public override string ToString()
{
return QdpMarket.MarketName;
}
}
}