Overall Statistics
Total Trades
216
Average Win
0%
Average Loss
0%
Compounding Annual Return
1135.673%
Drawdown
1.700%
Expectancy
0
Net Profit
0%
Sharpe Ratio
11.225
Loss Rate
0%
Win Rate
0%
Profit-Loss Ratio
0
Alpha
1.742
Beta
-1.361
Annual Standard Deviation
0.078
Annual Variance
0.006
Information Ratio
1.718
Tracking Error
0.135
Treynor Ratio
-0.64
Total Fees
$216.00
namespace QuantConnect {   

	public class Step2 : QCAlgorithm {
		//static String[] symbols = {"SPY", "XLF", "GDX", "EEM", "USO", "EWZ", "UVXY", "JNUG", "GDXJ", "IWM", "XOP", "QQQ", "EFA", "XLE", "NUGT", "IEMG", "DUST", "XIV", "FXI", "TZA", "VWO", "XLK", "AMLP", "HYG", "XLI", "XLU", "TLT", "RSX", "UGAZ", "UCO", "GLD", "TVIX", "UNG", "SLV", "UWT", "XRT", "XBI", "DGAZ", "SDS", "VEA", "JNK", "LQD", "XLV", "XLP", "JDST", "EZU", "IAU", "KRE", "BAC", "GE", "X", "F", "AMD", "CHK", "ITUB", "NOK", "INO", "ABEV", "VALE", "AKS", "PBR", "RAD", "WFT", "SIRI", "CSCO", "CHS", "PFE", "MU", "ECA", "INTC", "NVDA", "CLF", "RF", "VRX", "AAPL", "LOW", "AUY", "STNG", "SRC", "SWN", "KMI", "FB", "BBD", "CMCSA", "GLYC", "FCAU", "C", "AVP", "VZ", "T", "TWTR", "FGL", "FCX", "OAS", "MSFT", "TEVA", "SNAP", "WLL", "HUN"};
		static String[] symbols = {"QQQ", "GDX", "EEM", "USO"};
		int size = (int) (1 * 7.5 * 60 * 60);
		float threshold = 0.001f;
		int timeStart = 0;
		int timeEnd = 60;
		int consolidate = 15;
		int scount = symbols.Count();
		int i=0;
		int j=0;
		string sym1 = null;
		List<TradeBar> hist1 = null;
		string sym2 = null;
		List<TradeBar> hist2 = null;

		public override void Initialize() {
			Debug("---> Initialize - Start");
			DateTime startTime = new DateTime(2017, 5, 22, 10, 0, 0);
			DateTime endTime = new DateTime(2017, 5, 22, 10, 0, 10);
			SetStartDate(startTime);
			SetEndDate(endTime);

			SetCash(250000);
			
			foreach (string sym in symbols) {
				AddEquity(sym, Resolution.Second);
			}
			Debug("---> Initialize - End");
		}

		public override void OnData(Slice data) {
			//Debug("->0 " + i + ":" + scount);
			if (i==scount) {
				return;
			}
			if (sym1 == null) {
				sym1 = symbols[i];
				hist1 = History(sym1, size).ToList();
			}
			
			if (j == i) {
				j++;
			}

			if (j == scount) {
				j = 0;
				i++;
				sym1 = null;
				hist1.Clear();
				hist1 = null;
				GC.Collect();
				GC.WaitForPendingFinalizers();
				return;
			}
			
			//Debug("->1");
			if (sym2 == null) {
				sym2 = symbols[j];
				hist2 = History(sym2, size).ToList();
			}

			//Debug("->2");

			//Debug(sym1 + ":" + sym2 + ":" + hist1.Count() + " - " + hist2.Count());
			for (int d=timeStart; d<timeEnd; d++) {
				for (int c=1; c<consolidate; ++c) {
					float correlation = calc(hist1, hist2, d, c);
					if (correlation > threshold || correlation < -threshold) {
						string s = sym1 + ":" + sym2 + ":" + d + ":" + c + "\t" + correlation;
						Debug(s);
						MarketOrder(sym2, 100, false);
					}
				}
			}
			
			hist2.Clear();
			hist2 = null;

			//Debug("->3");

			j++;
			sym2 = null;
		}
		
		public override void OnEndOfAlgorithm() {
			Debug("OnEndOfAlgorithm");
		}
		
		private float calc(List<TradeBar> hist1, List<TradeBar> hist2, int delay, int cns) {
			//Debug("->4");
			int len1 = hist1.Count();
			int len2 = hist2.Count();
			int len = (len1 < len2) ? len1 : len2;
			len -= cns;
			List<float> list1 = new List<float>();
			List<float> list2 = new List<float>();
			for (int i=0; i<len; i+=cns) {
				float f1 = f(hist1, i, i+cns);
				list1.Add(f1);
				float f2 = f(hist2, i, i+cns);
				list2.Add(f2);
			}

			//Debug("->5");

			//Debug(String.Join("; ", list1));
			
			int cnt1 = list2.Count();
			List<float> list2delayed = new List<float>();
			for (int i=delay; i<cnt1; ++i) {
				float l2f = list2[i];
				list2delayed.Add(l2f);
			}

			//Debug("->6 " + String.Join("; ", list2delayed));
			
			list2.Clear();
			list2 = null;
			
			float correlation = Correlation(list1, list2delayed);

			list1.Clear();
			list1 = null;

			list2delayed.Clear();
			list2delayed = null;

			return correlation;
		}
		
		private float f(List<TradeBar> bars, int s, int e) {
			TradeBar bar1 = bars[s];
			TradeBar bar11 = bars[e-1];
			float open = (float) bar11.Open;
			float high = 0;
			float low = 100000000f;
			float close = (float) bar1.Close;
			for (int i=s; i<e; ++i) {
				TradeBar bar = bars[i];
				float l = (float) bar.Low;
				float h = (float) bar.High;
				if (l < low) {
					low = l;
				}
				if (h > high) {
					high = h;
				}
			}
			float half = (high + low) / 2;
			float f = 0;
			if (close > open) {
				if (close > half) {
					f = 2;
				} else {
					f = 1;
				}
			} else {
				if (close > half) {
					f = -1;
				} else {
					f = -2;
				}
			}
			return f;
		}

		private float Correlation(List<float> xs, List<float> ys) {
			// sums of x, y, x squared etc.
			float sx = 0;
			float sy = 0;
			float sxx = 0;
			float syy = 0;
			float sxy = 0;
		
			int n1 = xs.Count();
			int n2 = ys.Count();
			int n = (n1 < n2) ? n1 : n2;

			for (int i=0; i<n; ++i) {
				float x = xs[i];
				float y = ys[i];
				sx += x;
				sy += y;
				sxx += x * x;
				syy += y * y;
				sxy += x * y;
			}
		
			// covariation
			float cov = sxy / n - sx * sy / n / n;
			// standard error of x
			double sigmaX = Math.Sqrt(sxx / n -  sx * sx / n / n);
			// standard error of y
			double sigmaY = Math.Sqrt(syy / n -  sy * sy / n / n);
		
			// correlation is just a normalized covariation
			return (float) (cov / sigmaX / sigmaY);
		}

	}
}