/// <summary>
 /// For Black-Scholes-Merton model price calculation relies <see cref="IOptionPriceModel"/> of the security
 /// </summary>
 /// <param name="maximumPercentDeviation">The maximum percent deviation. This value is in percent space,
 ///     so a value of 1m is equal to 1%.</param>
 /// <param name="referenceDate">current reference date</param>
 /// <returns>A new decimal suitable for usage as new security price</returns>
 public decimal NextValue(decimal maximumPercentDeviation, DateTime referenceDate)
 {
     return(_option.PriceModel
            .Evaluate(
                _option,
                null,
                OptionContract.Create(
                    _option.Symbol,
                    _option.Symbol.Underlying,
                    referenceDate,
                    _option,
                    _option.Underlying.Price
                    ))
            .TheoreticalPrice);
 }
Exemplo n.º 2
0
        private bool HandleOptionData(DateTime algorithmTime, BaseData baseData, OptionChains optionChains, ISecurityPrice security, Lazy <Slice> sliceFuture, IReadOnlyDictionary <Symbol, BaseData> optionUnderlyingUpdates)
        {
            var symbol = baseData.Symbol;

            OptionChain chain;
            var         canonical = symbol.Canonical;

            if (!optionChains.TryGetValue(canonical, out chain))
            {
                chain = new OptionChain(canonical, algorithmTime);
                optionChains[canonical] = chain;
            }

            // set the underlying current data point in the option chain
            var option = security as IOptionPrice;

            if (option != null)
            {
                if (option.Underlying == null)
                {
                    Log.Error($"TimeSlice.HandleOptionData(): {algorithmTime}: Option underlying is null");
                    return(false);
                }

                BaseData underlyingData;
                if (!optionUnderlyingUpdates.TryGetValue(option.Underlying.Symbol, out underlyingData))
                {
                    underlyingData = option.Underlying.GetLastData();
                }

                if (underlyingData == null)
                {
                    Log.Error($"TimeSlice.HandleOptionData(): {algorithmTime}: Option underlying GetLastData returned null");
                    return(false);
                }
                chain.Underlying = underlyingData;
            }

            var universeData = baseData as BaseDataCollection;

            if (universeData != null)
            {
                if (universeData.Underlying != null)
                {
                    foreach (var addedContract in chain.Contracts)
                    {
                        addedContract.Value.UnderlyingLastPrice = chain.Underlying.Price;
                    }
                }
                foreach (var contractSymbol in universeData.FilteredContracts)
                {
                    chain.FilteredContracts.Add(contractSymbol);
                }
                return(false);
            }

            OptionContract contract;

            if (!chain.Contracts.TryGetValue(baseData.Symbol, out contract))
            {
                contract = OptionContract.Create(baseData, security, chain.Underlying.Price);

                chain.Contracts[baseData.Symbol] = contract;

                if (option != null)
                {
                    contract.SetOptionPriceModel(() => option.EvaluatePriceModel(sliceFuture.Value, contract));
                }
            }

            // populate ticks and tradebars dictionaries with no aux data
            switch (baseData.DataType)
            {
            case MarketDataType.Tick:
                var tick = (Tick)baseData;
                chain.Ticks.Add(tick.Symbol, tick);
                UpdateContract(contract, tick);
                break;

            case MarketDataType.TradeBar:
                var tradeBar = (TradeBar)baseData;
                chain.TradeBars[symbol] = tradeBar;
                UpdateContract(contract, tradeBar);
                break;

            case MarketDataType.QuoteBar:
                var quote = (QuoteBar)baseData;
                chain.QuoteBars[symbol] = quote;
                UpdateContract(contract, quote);
                break;

            case MarketDataType.Base:
                chain.AddAuxData(baseData);
                break;
            }
            return(true);
        }