Overall Statistics
Total Trades
51
Average Win
0.21%
Average Loss
-0.24%
Compounding Annual Return
-1.018%
Drawdown
9.000%
Expectancy
-0.655
Net Profit
-1.121%
Sharpe Ratio
-0.071
Loss Rate
82%
Win Rate
18%
Profit-Loss Ratio
0.90
Alpha
-0.031
Beta
0.348
Annual Standard Deviation
0.076
Annual Variance
0.006
Information Ratio
-0.773
Tracking Error
0.103
Treynor Ratio
-0.016
Total Fees
$51.00
using System;
using System.Collections.Concurrent;
using System.Linq;
using QuantConnect.Data.Market;
using QuantConnect.Data.UniverseSelection;
using QuantConnect.Indicators;

namespace QuantConnect.Algorithm.CSharp
{
    
    // mittelwert_neu = mittelwert_bisher - (mittelwert_bisher - neuer_wert)/anzahl_werte 
    
    /// <summary>
    /// tbd 
    /// </summary>
    public class UW_Simplify_V3 : QCAlgorithm
    {
        private Symbol _spy = QuantConnect.Symbol.Create("SPY", SecurityType.Equity, Market.USA);
        private SecurityChanges _changes = SecurityChanges.None;

        private DateTime TestDate = new DateTime(2016,10,22);
    	//private readonly Dictionary<Symbol, SymbolData> Data = new Dictionary<Symbol, SymbolData>();
        
        // holds our coarse fundamental indicators by symbol
        private readonly ConcurrentDictionary<Symbol, SelectionData> _averages = new ConcurrentDictionary<Symbol, SelectionData>();
        const decimal Tolerance = 0.01m;
        private const int Count = 30;
        private const decimal TargetPercent = 0.1m;
        private const decimal tpPercent = 0.05m;

        Dictionary<Symbol, SymbolData> MySymbolData = new Dictionary<Symbol, SymbolData>();

        // class used to improve readability of the coarse selection function
        private class SelectionData
        {
            public readonly ExponentialMovingAverage Fast;
            public readonly ExponentialMovingAverage Slow;
            public readonly ExponentialMovingAverage Slowest;

            public SelectionData()
            {
                Fast = new ExponentialMovingAverage(20);
                Slow = new ExponentialMovingAverage(30);
                Slowest = new ExponentialMovingAverage(100);
            }
        
            // computes an object score of how much large the fast is than the slow
            public decimal ScaledDelta
            {
                get { return (Fast - Slow)/((Fast + Slow)/2m); }
            }

            // updates the EMA50 and EMA100 indicators, returning true when they're both ready
            public bool Update(DateTime time, decimal value)
            {
                return Fast.Update(time, value) && Slow.Update(time, value)  && Slowest.Update(time, value); 
            }
        }

        /// <summary>
        /// Initialise the data and resolution required, as well as the cash and start-end dates for your algorithm. All algorithms must initialized.
        /// </summary>
        public override void Initialize()
        {
            SetStartDate(2015, 10, 07);  //Set Start Date
            SetEndDate(2016, 11, 11);    //Set End Date
            SetCash(25000);             //Set Strategy Cash

           // AddEquity("SPY", Resolution.Daily);
            UniverseSettings.Resolution = Resolution.Daily;

            AddUniverse(coarse =>
            {
                return (from cf in coarse
                        // grab th SelectionData instance for this symbol
                        let avg = _averages.GetOrAdd(cf.Symbol, sym => new SelectionData())
                        // Update returns true when the indicators are ready, so don't accept until they are
                        where avg.Update(cf.EndTime, cf.Price)
                        // only pick symbols who have their price over their 200 day ema
                         where cf.Price > avg.Slowest
                        // only pick symbols who have their 50 day ema over their 200 day ema
                        where avg.Slow > avg.Slowest
                        // only pick symbols who have their 20 day ema over their 20 day ema
                        where avg.Fast> avg.Slow
                        // prefer symbols with a larger delta by percentage between the two averages
                        orderby avg.ScaledDelta descending
                        // we only need to return the symbol and return 'Count' symbols
                        select cf.Symbol).Take(Count);
            });
            
            Debug(" End Init");
            
            foreach (var added in _changes.AddedSecurities) 
            {
              if (!MySymbolData.ContainsKey(added.Symbol)) 
              {
                 MySymbolData.Add(added.Symbol, new SymbolData(added.Symbol, this));
                 Debug(" in Init added " + added.Symbol);
              	
              }
  
            }

        } // end Initialize



        /// <summary>
        /// OnData event is the primary entry point for your algorithm. Each new data point will be pumped in here.
        /// </summary>
        /// <param name="data">Slice object keyed by symbol containing the stock data</param>
        public override void OnData(Slice data)
        {
            if (!Portfolio.Invested)
            {
                SetHoldings(_spy, 1);
                Debug("Purchased Stock");
            }
        
            if (_changes == SecurityChanges.None) return;

            foreach (var Stock in MySymbolData.Values)
        	{

        		if (data.ContainsKey(Stock.Symbol)) return;
            	if (IsWarmingUp) return;   		

               //  Stock.Update(Stock.Security, Stock.Security.Time);
               // Stock.lSMA.Update(data.EndTime, data.Close);
      
           	    Debug("  >> " + Stock.Security + " " + Stock.Security.Price + " "  + Stock.hSMA  + " "  + Stock.lSMA);            	

				if ( Portfolio.Count < 5)
            	{
            		
                	if ( Stock.Security.Price > Stock.hSMA )
                	{
                	    Log("BUY  >> " + Stock.Security.Price);
                	    Debug("BUY  >> " + Stock.Security.Price);
                	    SetHoldings(Stock.Symbol, 0.5m);
                	    var takeProfit = Stock.Security.Price*tpPercent;
                	    LimitOrder(Stock.Symbol, - Stock.Quantity, takeProfit);
                	}
                	
                	
                 if (Stock.Quantity > 0 && Stock.Security.Price <= Stock.lSMA)
            	   {
            	       Log("SELL >> " + Stock.Security.Price);
            	       Debug("SELL >> " + Stock.Security.Price);
            	        Liquidate(Stock.Symbol);    
            	   }
                	
            	}


        	}

            // liquidate securities removed from our universe
            foreach (var security in _changes.RemovedSecurities)
            {
                if (security.Invested)
                {
                    Liquidate(security.Symbol);
                }
            }

            // we'll simply go long each security we added to the universe
            foreach (var security in _changes.AddedSecurities)
            {
                SetHoldings(security.Symbol, 1);
            }
           
            foreach (var security in _changes.AddedSecurities) {
                if (Time.Date == new DateTime(2016,10,13) )
            	 Debug("1 Symbol= " + Time.ToShortDateString() + " " + security.Symbol.ToString()  + " "  );
            }
        } // end OnData
        
        
        public override void OnSecuritiesChanged(SecurityChanges changes)
        {
            _changes = changes;
            Debug(Time.Date.ToShortDateString() + "  2 Number=" + _changes.AddedSecurities.Count.ToString() );
            foreach (var security in _changes.AddedSecurities)
            {
                 Debug("Added " + security.Symbol);
                 if (!MySymbolData.ContainsKey(security.Symbol)) 
                 {
                    MySymbolData.Add(security.Symbol, new SymbolData(security.Symbol, this));
                    Debug("Added to Data -> " + security.Symbol);
                 }
            }

            foreach (var security in _changes.RemovedSecurities)
            {
                 Debug("Removed " + security.Symbol);
            }

           
        } // end OnSecuritiesChanged
    }  // end class
    
    
    /*
    You will need to create a class similar to SelectionData, say SymbolData, 
    and create a dictionary to hold its values Dictionary<Symbol, SymbolData> 
    to save the SMA of High and Low to be used as trading signal.
    */
    

    class SymbolData
	{
	  	public string Symbol;
	  	private const int hPeriods = 8;
		public int rollingWindowSize = 1;
        public readonly Security Security;
       
       
        public int Quantity
        {
            get { return (int)Security.Holdings.Quantity; }
        }

        public readonly Identity Close;
		
	  	public readonly SimpleMovingAverage hSMA;
	  	public readonly SimpleMovingAverage lSMA;
		public readonly RollingWindow<TradeBar> lastDay;



	  	public SymbolData(string symbol, QCAlgorithm algorithm)
		{
    	   Symbol = symbol;
    	   Security = algorithm.Securities[symbol];
           Close = algorithm.Identity(symbol);
    	   hSMA = algorithm.SMA(symbol, hPeriods, Resolution.Daily, Field.High);
    	   lSMA = algorithm.SMA(symbol, hPeriods, Resolution.Daily, Field.Low);
           lastDay = new RollingWindow<TradeBar>(rollingWindowSize);;
    	}
    	
    	 public bool Update(CoarseFundamental coarse)
         {
         	lSMA.Update(coarse.EndTime, coarse.Value);
            return hSMA.Update(coarse.EndTime, coarse.Value );
         }
    	
    	public bool IsReady
        {
                get { return Close.IsReady && hSMA.IsReady && lSMA.IsReady && lastDay.IsReady; }
        } 
	}   // end class  
    
}  // end namespace