yearlyReturnDF = pd.DataFrame(subDict)

mu, sigma, covar = getStats(yearlyReturnDF, y1)

targetReturn = mu.min()
w1, r1, s1 = solveMarkowitzWithShorting(yearlyReturnDF, targetReturn, y1)

targetReturn = mu.max()
w2, r2, s2 = solveMarkowitzWithShorting(yearlyReturnDF, targetReturn, y1)

optimalSigma = []
optimalReturn = []
# sigmaMat = covar.as_matrix()
for alpha in np.linspace(0,1,endpoint=True):
	curWeight = alpha*w1 + (1-alpha)*w2
	r, s = calculateWeightedPortfolio(curWeight, mu.as_matrix(), covar.as_matrix())
	optimalSigma.append(s)	
	optimalReturn.append(r)

# output to static HTML file
plotTitle = "Portfolio Diagram With Shorting"
output_file("Portfolio.html", title=plotTitle)
p2 = figure(plot_width=1000)
p2.title = plotTitle
p2.xaxis.axis_label = "sigma"
p2.yaxis.axis_label = "return"
# A = (mu.iloc[0] * sigma.iloc[1] + mu.iloc[1] * sigma.iloc[0]) / (sigma.iloc[1] + sigma.iloc[0])
# p2.line([0,sigma.iloc[1]], [A, mu.iloc[1]])
# p2.line([0,sigma.iloc[0]], [A, mu.iloc[0]])
# p2.line([sigma.iloc[0],sigma.iloc[1]], [mu.iloc[0], mu.iloc[1]])
p2.line(optimalSigma, optimalReturn, line_width=2, color='black', legend='Markowitz Efficient')
# Adding a column to covar to incorporate the lambda lagrange multiplier, which is appended to w
bigS = np.vstack((covar.T, one)).T
# Adding a row on the bottom (and finishing the above column) to include the normalized w condition.
bottom = np.hstack((one,0))
bigS = np.vstack((bigS,bottom))

bigMu = np.hstack((mu,0.))
bigRHS = np.zeros_like(bigMu)
bigRHS[-1] = 1.

wsol_opt = np.linalg.solve(bigS,bigRHS + bigMu)
wsol_opt, lam_opt = wsol_opt[:-1], wsol_opt[-1]
gam_opt = 0.

mu_opt, std_opt = calculateWeightedPortfolio(wsol_opt, mu, covar)
nu_opt = mu_opt - 0.5*std_opt**2

# So that above was the log-optimal, but no one would ever use it.  Find the minimum volatility solution and then use the two-fund theorem to get the efficient frontier.

minS = np.zeros((numStocks+1, numStocks+1))
minS[:numStocks, :numStocks] = covar
minS[:,-1] = -1
minS[-1,:] = 1
minS[-1,-1] = 0

minRHS = np.zeros(numStocks+1)
minRHS[-1] = 1

wsol_min = np.linalg.solve(minS,minRHS)
wsol_min, lam_min = wsol_min[:-1], wsol_min[-1]