|
import pandas as pd |
|
import numpy as np |
|
from datetime import datetime as dt |
|
from pypfopt.efficient_frontier import EfficientFrontier |
|
import streamlit as st |
|
import plotly.graph_objects as go |
|
import plotly.express as px |
|
|
|
def ef_viz(stock_df,choices): |
|
st.write("EF Visualization KOI EDITS") |
|
symbols, weights, investment = choices.values() |
|
tickers = symbols |
|
|
|
|
|
st.write(tickers) |
|
|
|
|
|
|
|
|
|
stock_dff = stock_df.copy() |
|
stock_dff['Date'] = pd.to_datetime(stock_dff['Date']) |
|
|
|
|
|
|
|
|
|
ind_er_df = stock_dff.resample('Y', on = 'Date').last().pct_change().mean() |
|
ind_er = ind_er_df[tickers] |
|
|
|
ann_sd = stock_df[tickers].pct_change().apply(lambda x: np.log(1+x)).std().apply(lambda x: x*np.sqrt(250)) |
|
assets = pd.concat([ind_er, ann_sd], axis=1) |
|
assets.columns = ['Returns', 'Volatility'] |
|
assets |
|
st.write(assets) |
|
ln_pct_change = stock_df[tickers].pct_change().apply(lambda x: np.log(1+x))[1:] |
|
|
|
cov_matrix =ln_pct_change.cov() |
|
|
|
|
|
p_ret = [] |
|
p_vol = [] |
|
p_weights = [] |
|
|
|
num_assets = len(tickers) |
|
num_portfolios = 10000 |
|
|
|
for portfolio in range(num_portfolios): |
|
weights = np.random.random(num_assets) |
|
weights = weights/np.sum(weights) |
|
p_weights.append(weights) |
|
returns = np.dot(weights, ind_er) |
|
|
|
p_ret.append(returns) |
|
var = cov_matrix.mul(weights, axis=0).mul(weights, axis=1).sum().sum() |
|
sd = np.sqrt(var) |
|
ann_sd = sd*np.sqrt(250) |
|
p_vol.append(ann_sd) |
|
|
|
data = {'Returns':p_ret, 'Volatility':p_vol} |
|
|
|
for counter, symbol in enumerate(stock_df[tickers].columns.tolist()): |
|
|
|
data[symbol] = [w[counter] for w in p_weights] |
|
|
|
port_ef_df = pd.DataFrame(data) |
|
st.write(port_ef_df[tickers].T) |
|
rf = 0.041 |
|
min_vol_port = port_ef_df.iloc[port_ef_df['Volatility'].idxmin()] |
|
optimal_risky_port = port_ef_df.iloc[((port_ef_df['Returns']-rf)/port_ef_df['Volatility']).idxmax()] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
fig = px.scatter(port_ef_df, 'Volatility', 'Returns', size='Returns', size_max=20, color='Volatility', \ |
|
custom_data=tickers) |
|
fig.update_traces(hovertemplate="<br>".join([ |
|
"%{tickers[0]}:%{custom_data[0]}", |
|
"%{tickers[1]}:%{custom_data[1]}", |
|
"%{tickers[2]}:%{custom_data[2]}", |
|
"%{tickers[3]}:%{custom_data[3]}" |
|
|
|
]) |
|
) |
|
|
|
st.plotly_chart(fig, use_container_width=True) |
|
|