コード例 #1
0
        // Updates this model using the new price information in the specified security instance
        // Update is a mandatory method
        public void Update(Security security, BaseData data)
        {
            var timeSinceLastUpdate = data.EndTime - _lastUpdate;

            if (timeSinceLastUpdate >= _periodSpan && data.Price > 0m)
            {
                if (_lastPrice > 0)
                {
                    _window.Add(data.Price / _lastPrice - 1.0m);
                    _needsUpdate = _window.IsReady;
                }

                _lastUpdate = data.EndTime;
                _lastPrice  = data.Price;
            }

            if (_window.Count() < 2)
            {
                Volatility = 0;
                return;
            }

            if (_needsUpdate)
            {
                _needsUpdate = false;
                var mean = _window.Average();
                var std  = Math.Sqrt((double)_window.Sum(x => (x - mean) * (x - mean)) / _window.Count());
                Volatility = Convert.ToDecimal(std * Math.Sqrt(252d));
            }
        }
コード例 #2
0
        public void WhenComputing_Then_ResultIsTheSumOfAllDataInTheWindow()
        {
            const int period = 5;
            var       sut    = new SumComputation();

            var window = new RollingWindow <double>(period);

            for (int i = 0; i < 2 * period; i++)
            {
                window.Add(i);

                var result = sut.Compute(window);
                Assert.AreEqual(window.Sum(), result);
            }
        }
コード例 #3
0
        public void OnData(TradeBars data)
        {
            if (!_slow.IsReady)
            {
                _volume.Add(Securities[Symbol].Volume);
                _price.Add(Securities[Symbol].Price);
                return;
            }

            var averageVolume = _volume.Sum() / _volume.Count;
            var volumeSignal  = Securities[Symbol].Volume > averageVolume ||
                                _volume.Skip(_volume.Count - 7).Any(av => av > averageVolume);

            var holdings = Portfolio[Symbol].Quantity;

            if (_openStopMarketOrder != null && _openStopMarketOrder.Status != OrderStatus.Filled)
            {
                if (_openStopMarketOrder.Tag.Equals("long") && _price[0] < Securities[Symbol].Price)
                {
                    var newLongLimit = Securities[Symbol].Price * (1 - 0.05m);

                    _openStopMarketOrder.Update(new UpdateOrderFields
                    {
                        StopPrice = newLongLimit
                    });
                }
                else if (_openStopMarketOrder.Tag.Equals("short") && _price[0] > Securities[Symbol].Price)
                {
                    var newShortLimit = Securities[Symbol].Price * 1.05m;

                    _openStopMarketOrder.Update(new UpdateOrderFields
                    {
                        StopPrice = newShortLimit
                    });
                }
            }
            else if (holdings <= 0 && _fast > _slow * (1 + tolerance) && volumeSignal)
            {
                Log("BUY  >> " + Securities[Symbol].Price);
                //SetHoldings(Symbol, 1.0);

                var orderTicket = StopMarketOrder(Symbol, (int)(Portfolio.Cash / Securities[Symbol].Price), Securities[Symbol].Price * (1 - 0.05m), "long");

                _openStopMarketOrder?.Cancel();
                _openStopMarketOrder = orderTicket;
            }
            else if (holdings >= 0 && _fast < _slow * (1 - tolerance) && volumeSignal)
            {
                Log("SELL >> " + Securities[Symbol].Price);
                //SetHoldings(Symbol, -1.0);

                var shortAmount = Portfolio[Symbol].HoldingsValue == 0 ? Portfolio.Cash : Portfolio[Symbol].HoldingsValue;
                var orderTicket = StopMarketOrder(Symbol, -(int)(shortAmount / Securities[Symbol].Price), Securities[Symbol].Price * 1.05m, "short");

                _openStopMarketOrder?.Cancel();
                _openStopMarketOrder = orderTicket;
            }

            _volume.Add(Securities[Symbol].Volume);
            _price.Add(Securities[Symbol].Price);

            Plot("SMA Cross", "400", _slow.RollingSum / _slow.Period);
            Plot("SMA Cross", "100", _fast.RollingSum / _fast.Period);
            Plot("SMA Cross", "Price", Securities[Symbol].Price);
        }