Spaces:
Running
Running
import streamlit as st | |
import pandas as pd | |
import numpy as np | |
import yfinance as yf | |
import matplotlib.pyplot as plt | |
from scipy.optimize import minimize | |
# Fungsi untuk mengunduh data saham | |
def get_stock_data(tickers, start, end): | |
data = yf.download(tickers, start=start, end=end)['Adj Close'] | |
return data | |
# Fungsi untuk menghitung return harian | |
def calculate_daily_returns(data): | |
return data.pct_change().dropna() | |
# Fungsi untuk menghitung portofolio optimal dengan Model Markowitz | |
def optimize_portfolio(returns): | |
num_assets = len(returns.columns) | |
weights = np.random.random(num_assets) | |
weights /= np.sum(weights) | |
def portfolio_performance(weights): | |
port_return = np.sum(returns.mean() * weights) * 252 | |
port_volatility = np.sqrt(np.dot(weights.T, np.dot(returns.cov() * 252, weights))) | |
return port_volatility | |
constraints = ({'type': 'eq', 'fun': lambda x: np.sum(x) - 1}) | |
bounds = tuple((0, 1) for _ in range(num_assets)) | |
result = minimize(portfolio_performance, weights, method='SLSQP', bounds=bounds, constraints=constraints) | |
return result.x | |
# Streamlit UI | |
st.title("Analisis Portofolio Saham Model Markowitz") | |
# Input pengguna untuk daftar saham | |
tickers = st.text_input("Masukkan kode saham (pisahkan dengan koma)", "BBCA.JK,TLKM.JK,UNVR.JK") | |
start_date = st.date_input("Pilih tanggal mulai", pd.to_datetime("2020-01-01")) | |
end_date = st.date_input("Pilih tanggal akhir", pd.to_datetime("2020-12-31")) | |
if st.button("Analisis"): | |
tickers_list = [t.strip() for t in tickers.split(',')] | |
data = get_stock_data(tickers_list, start_date, end_date) | |
if not data.empty: | |
st.write("Data Harga Saham") | |
st.line_chart(data) | |
returns = calculate_daily_returns(data) | |
optimal_weights = optimize_portfolio(returns) | |
st.write("Bobot Optimal Portofolio:") | |
for ticker, weight in zip(tickers_list, optimal_weights): | |
st.write(f"{ticker}: {weight:.2%}") | |
# Visualisasi Portofolio | |
fig, ax = plt.subplots() | |
ax.pie(optimal_weights, labels=tickers_list, autopct='%1.1f%%', startangle=90) | |
ax.axis("equal") | |
st.pyplot(fig) | |
else: | |
st.error("Gagal mengambil data saham. Pastikan kode saham benar.") |