Пример #1
0
        /// <summary>
        /// Values at.
        /// </summary>
        /// <param name="axisValue">The axis value.</param>
        /// <param name="extrapolation">if set to <c>true</c> [extrapolation].</param>
        /// <returns></returns>
        public double ValueAt(double axisValue, bool extrapolation)
        {
            string        engineHandle      = SettingsHandle;
            decimal       time              = Convert.ToDecimal(ExpiryTime);
            const decimal tenor             = 0;
            var           calibrationEngine =
                new SABRCalibrationEngine(engineHandle,
                                          CalibrationSettings,
                                          EngineHandles,
                                          AtmVolatility,
                                          AssetPrice,
                                          time,
                                          tenor
                                          );

            calibrationEngine.CalibrateInterpSABRModel();
            var sabrParameters = new SABRParameters(calibrationEngine.GetSABRParameters.Alpha,
                                                    calibrationEngine.GetSABRParameters.Beta,
                                                    calibrationEngine.GetSABRParameters.Nu,
                                                    calibrationEngine.GetSABRParameters.Rho);
            var     sabrImpliedVol = new SABRImpliedVolatility(sabrParameters, false);
            var     value          = Convert.ToDecimal(axisValue) * AssetPrice;
            string  errMsg         = "Error interpolating";
            decimal result         = 0.0m;

            sabrImpliedVol.SABRInterpolatedVolatility(AssetPrice, time, value, ref errMsg, ref result, true);
            return(Convert.ToDouble(result));
        }
        /// <summary>
        /// Computes the Caplet volatility smile at a particular Caplet expiry.
        /// Exception: ArgumentException, System.Exception
        /// </summary>
        /// <param name="logger">The logger.</param>
        /// <param name="cache">The cache.</param>
        /// <param name="nameSpace">The clients namespace</param>
        /// <param name="expiry">Caplet expiry.</param>
        /// <param name="strikes">List of strikes for which to compute the
        /// implied volatility.</param>
        /// <returns>List that contains the implied volatility computed
        /// at each strike.</returns>
        public List <decimal> ComputeVolatilitySmile
            (ILogger logger, ICoreCache cache, string nameSpace, DateTime expiry, List <decimal> strikes)
        {
            // Check that the list of strikes is not empty.
            if (strikes.Count == 0)
            {
                throw new ArgumentException("Empty list of strikes found by Caplet smile", nameof(strikes));
            }
            CalibrateSABREngine(logger, cache, nameSpace, expiry);
            // Compute the Caplet volatility at each strike.
            var volatilities = new List <decimal>(); // answers
            var impliedVolObj
                = new SABRImpliedVolatility(_sabrEngine.GetSABRParameters, false);
            var errorMessage = "";
            var result       = -1.0m;

            foreach (var strike in strikes)
            {
                var success = impliedVolObj.SABRInterpolatedVolatility
                                  (_assetPrice,
                                  _excerciseTime,
                                  strike,
                                  ref errorMessage,
                                  ref result,
                                  true);
                if (!success)
                {
                    throw new Exception(errorMessage);
                }
                // Volatility was successfully computed: store result.
                volatilities.Add(result);
            }
            return(volatilities);
        }
        public void TestSABRImpliedVolatility()
        {
            SABRImpliedVolatility impliedVolObj =
                new SABRImpliedVolatility(_sabrParameters,
                                          _checkSABRParameters);

            Assert.IsNotNull(impliedVolObj);
        }
Пример #4
0
        /// <summary>
        /// Calculate the SABR implied volatility for the strike value.
        /// This method uses the calibration engine indexed by the exerciseTime/assetCode pair
        /// When an ATM engine is used then the assetCode is ignored.
        /// </summary>
        /// <param name="engineHandle">The CalibrationEngine to use</param>
        /// <param name="exerciseTime">Option Expiry index</param>
        /// <param name="assetCode">Swap Tenor index</param>
        /// <param name="strikes">The strikes to calculate Volatility for</param>
        /// <returns></returns>
        public decimal[] SABRInterpolateVolatilities(string engineHandle, string exerciseTime, string assetCode,
                                                     decimal[] strikes)
        {
            // Only process if the engine object holder holds the engine for this exercise/asset key
            if (!_sabrEngines.ContainsKey(engineHandle))
            {
                throw new System.Exception("Calibration Engine " + engineHandle + " not found.");
            }
            // Extract the information we need from this engine holder
            SortedDictionary <SABRKey, SABRCalibrationEngine> engine = _sabrEngines[engineHandle];
            var key = new SABRKey(GenerateTenorLabel(exerciseTime), GenerateTenorLabel(assetCode));

            // Check that the engine for this exercise/asset key exists
            if (!engine.ContainsKey(key))
            {
                throw new System.Exception("The Calibration Engine with Key(" + exerciseTime + "," + assetCode + ") not found.");
            }
            SABRCalibrationEngine calibrationEngine = engine[key];

            if (!calibrationEngine.IsSABRModelCalibrated)
            {
                throw new ArgumentException(string.Format(CultureInfo.CurrentCulture,
                                                          "SABR Engine with key: {0}:{1} is not calibrated",
                                                          new object[] { key.Expiry, key.Tenor }));
            }
            // Create SABRImpliedVolatility parameters
            decimal assetPrice = _engineRatesGrid.ContainsKey(engineHandle)
                                     ? _engineRatesGrid[engineHandle].GetAssetPrice(exerciseTime, assetCode)
                                     : calibrationEngine.AssetPrice;
            decimal expiry = GenerateDayValue(exerciseTime, 365.0m);
            // build an ImpliedVolatility object
            SABRParameters parameters = calibrationEngine.GetSABRParameters;
            var            vol        = new SABRImpliedVolatility(parameters, true);
            // value the strike (interpolate as necessary)
            var results = new List <decimal>(strikes.Length);

            foreach (decimal strike in strikes)
            {
                string  errmsg = "";
                decimal result = 0;
                if (!vol.SABRInterpolatedVolatility(assetPrice, expiry, strike, ref errmsg, ref result, true))
                {
                    throw new System.Exception(errmsg);
                }
                results.Add(result);
            }
            return(results.ToArray());
        }
        /// <summary>
        /// Calculate the SABR implied volatility for the strike value.
        /// This method uses the calibration engine indexed by the exerciseTime/assetCode pair
        /// When an ATM engine is used then the assetCode is ignored.
        /// </summary>
        /// <param name="engineHandle">The CalibrationEngine to use</param>
        /// <param name="exerciseTime">Option Expiry index</param>
        /// <param name="assetCode">Swap Tenor index</param>
        /// <param name="strike">The strike to calculate Volatility for</param>
        /// <returns></returns>
        public decimal SABRInterpolateVolatility(string engineHandle, string exerciseTime, string assetCode, decimal strike)
        {
            decimal result = 0;
            string  errmsg = "";

            // Only process if the engine object holder holds the engine for this exercise/asset key
            if (_sabrEngines.ContainsKey(engineHandle))
            {
                // Extract the information we need from this engine holder
                var engine = _sabrEngines[engineHandle];
                var key    = new SABRKey(SABRHelper.GenerateTenorLabel(exerciseTime), SABRHelper.GenerateTenorLabel(assetCode));
                // Check that the engine for this exercise/asset key exists
                if (engine.ContainsKey(key))
                {
                    SABRCalibrationEngine calibrationEngine = engine[key];
                    if (!calibrationEngine.IsSABRModelCalibrated)
                    {
                        throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, "SABR Engine with key: {0}:{1} is not calibrated", new object[] { key.Expiry, key.Tenor }));
                    }
                    // Create SABRImpliedVolatility parameters
                    decimal assetPrice  = _engineRatesGrid.ContainsKey(engineHandle) ? _engineRatesGrid[engineHandle].GetAssetPrice(exerciseTime, assetCode) : calibrationEngine.AssetPrice;
                    decimal strikeValue = strike;
                    var     expiry      = (decimal)SABRHelper.GenerateDayValue(exerciseTime, 365.0d);
                    //decimal strikeValue = strike / 100.0m;
                    // build an ImpliedVolatility object
                    SABRParameters parameters = calibrationEngine.GetSABRParameters;
                    var            vol        = new SABRImpliedVolatility(parameters, true);
                    // value the strike (interpolate as necessary)
                    if (!vol.SABRInterpolatedVolatility(assetPrice, expiry, strikeValue, ref errmsg, ref result, true))
                    {
                        throw new ArgumentException(errmsg);
                    }
                }
                else
                {
                    throw new ArgumentException("The Calibration Engine with Key(" + exerciseTime + "," + assetCode + ") not found.");
                }
            }
            else
            {
                throw new ArgumentException("Calibration Engine " + engineHandle + " not found.");
            }
            return(result);
        }
        public void TestSabrInterpolatedVolatilityComputeXDouble()
        {
            const double   Alpha          = 0.219540520585315;
            const double   Beta           = 1;
            const double   Nu             = 0.0000000000021506467396720648;
            const double   Rho            = 0.999999999999999;
            SABRParameters sabrParameters = new SABRParameters(Alpha, Beta, Nu, Rho);

            const double AssetPrice   = 0.07226393165;
            const double ExerciseTime = 1d / 12;
            const double Strike       = 0.0722905443874852823;
            const bool   CheckImpliedVolParameters = false;
            double       answer = 0;
            string       error  = "";

            SABRImpliedVolatility impliedVolObject = new SABRImpliedVolatility(sabrParameters, CheckImpliedVolParameters);

            bool result = impliedVolObject.SABRInterpolatedVolatility(AssetPrice, ExerciseTime, Strike,
                                                                      ref error, ref answer, CheckImpliedVolParameters);

            Assert.IsTrue(result);
            Assert.AreEqual("", error);
            Assert.AreEqual(6.72317387E-15, answer, 1E-23);
        }
        public void TestSABRInterpolatedVolatility()
        {
            #region Tests: SABR Implied Volatility for beta = 0.0

            // Test computation of the SABR implied volatility for
            // the case beta = 0.0.
            _alpha = 0.60897d / 100d;
            _beta  = 0.0d;
            _nu    = 32.0d / 100d;
            _rho   = 17.0d / 100d;
            _checkSABRParameters = false;
            SABRParameters sabrParameters1 =
                new SABRParameters(_alpha, _beta, _nu, _rho);

            SABRImpliedVolatility impliedVolObj1 =
                new SABRImpliedVolatility(sabrParameters1,
                                          _checkSABRParameters);

            // Strike = ATM - 200bp.
            _strike   = _assetPrice - 200.0d / 10000d;
            _expected = 23.96039d / 100d;
            const double tolerance1 = 1.0E-5d;

            _isSuccessful =
                impliedVolObj1.SABRInterpolatedVolatility(
                    _assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance1);

            // Strike = ATM.
            _strike   = _assetPrice;
            _expected = 15.99991d / 100d;

            _isSuccessful =
                impliedVolObj1.SABRInterpolatedVolatility(
                    _assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance1);

            // Strike = ATM + 200bp.
            _strike   = _assetPrice + 200.0d / 10000d;
            _expected = 15.62789d / 100d;

            _isSuccessful =
                impliedVolObj1.SABRInterpolatedVolatility(
                    _assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance1);

            #endregion Tests: SABR Implied Volatility for beta = 0.0

            #region Tests: SABR Implied Volatility for beta = 0.5

            // Test computation of the SABR implied volatility for
            // the case beta = 0.5.
            _alpha = 3.05473d / 100d;
            _beta  = 0.5d;
            _nu    = 34.0d / 100d;
            _rho   = -11.0d / 100d;
            _checkSABRParameters = false;
            SABRParameters sabrParameters2 =
                new SABRParameters(_alpha, _beta, _nu, _rho);

            SABRImpliedVolatility impliedVolObj2 =
                new SABRImpliedVolatility(sabrParameters2,
                                          _checkSABRParameters);

            // Strike = ATM - 200bp.
            _strike   = _assetPrice - 200.0d / 10000d;
            _expected = 23.73848d / 100d;
            const double tolerance2 = 1.0E-5d;

            _isSuccessful =
                impliedVolObj2.SABRInterpolatedVolatility(_assetPrice,
                                                          _exerciseTime,
                                                          _strike,
                                                          ref _errorMessage,
                                                          ref _result,
                                                          _checkSABRParameters);
            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance2);

            // Strike = ATM
            _strike   = _assetPrice;
            _expected = 16.00001d / 100d;

            _isSuccessful =
                impliedVolObj2.SABRInterpolatedVolatility(_assetPrice,
                                                          _exerciseTime,
                                                          _strike,
                                                          ref _errorMessage,
                                                          ref _result,
                                                          _checkSABRParameters);
            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance2);

            // Strike = ATM + 200bp
            _strike   = _assetPrice + 200.0d / 10000d;
            _expected = 15.75552d / 100d;

            _isSuccessful =
                impliedVolObj2.SABRInterpolatedVolatility(_assetPrice,
                                                          _exerciseTime,
                                                          _strike,
                                                          ref _errorMessage,
                                                          ref _result,
                                                          _checkSABRParameters);
            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance2);


            #endregion Tests: SABR Implied Volatility for beta = 0.5

            #region Tests: SABR Implied Volatility for beta = 1.0

            // Test computation of the SABR implied volatility for
            // the case beta = 1.0.
            _alpha = 15.53173d / 100d;
            _beta  = 1.0d;
            _nu    = 40.0d / 100d;
            _rho   = -33.0d / 100d;
            _checkSABRParameters = false;
            SABRParameters sabrParameters3 =
                new SABRParameters(_alpha, _beta, _nu, _rho);

            SABRImpliedVolatility impliedVolObj3 =
                new SABRImpliedVolatility(sabrParameters3,
                                          _checkSABRParameters);

            // Strike = ATM - 200bp.
            _strike   = _assetPrice - 200.0d / 10000d;
            _expected = 23.79395d / 100d;
            const double tolerance3 = 1.0E-5d;

            _isSuccessful =
                impliedVolObj3.SABRInterpolatedVolatility
                    (_assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance3);

            // Strike = ATM
            _strike   = _assetPrice;
            _expected = 16.00000d / 100d;

            _isSuccessful =
                impliedVolObj3.SABRInterpolatedVolatility
                    (_assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance3);

            // Strike = ATM + 200bp
            _strike   = _assetPrice + 200.0d / 10000d;
            _expected = 16.05579d / 100d;

            _isSuccessful =
                impliedVolObj3.SABRInterpolatedVolatility
                    (_assetPrice,
                    _exerciseTime,
                    _strike,
                    ref _errorMessage,
                    ref _result,
                    _checkImpliedVolParameters);

            Assert.IsTrue(_isSuccessful);
            Assert.AreEqual(_expected,
                            _result,
                            tolerance3);


            #endregion Tests: SABR Implied Volatility for beta = 1.0
        }