aiqtech commited on
Commit
4db4956
ยท
verified ยท
1 Parent(s): 27dfb77

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +32 -119
app.py CHANGED
@@ -1,136 +1,49 @@
1
  import gradio as gr
2
  import yfinance as yf
3
- from pypfopt.discrete_allocation import DiscreteAllocation, get_latest_prices
4
- from pypfopt import EfficientFrontier
5
- from pypfopt import risk_models
6
- from pypfopt import expected_returns
7
- from pypfopt import plotting
8
- import copy
9
- import numpy as np
10
  import pandas as pd
11
- import plotly.express as px
12
- import matplotlib.pyplot as plt
13
  from datetime import datetime
14
- from prophet import Prophet
15
 
16
- def predict_future_prices(ticker, periods=1825): # 5๋…„๊ฐ„์˜ ๋ฐ์ดํ„ฐ ์˜ˆ์ธก
17
- data = yf.download(ticker, start="2010-01-01")['Adj Close'].reset_index()
18
- data.rename(columns={'Date': 'ds', 'Adj Close': 'y'}, inplace=True)
19
-
20
- model = Prophet(daily_seasonality=False, weekly_seasonality=False, yearly_seasonality=True)
21
- model.fit(data)
22
 
23
- future = model.make_future_dataframe(periods=periods, freq='D')
24
- forecast = model.predict(future)
 
 
 
 
 
 
 
 
 
 
 
 
25
 
26
- fig = px.line(forecast, x='ds', y='yhat', title=f'5-Year Future Price Forecast for {ticker}')
27
- return fig, forecast[['ds', 'yhat', 'yhat_lower', 'yhat_upper']]
28
-
29
-
30
-
31
- def plot_cum_returns(data, title, initial_capital=1000):
32
- # ์ผ์ผ ๋ˆ„์  ์ˆ˜์ต๋ฅ  ๊ณ„์‚ฐ ๋ฐ ์‹œ๊ฐํ™”
33
- daily_cum_returns = (1 + data.dropna().pct_change()).cumprod() * initial_capital
34
- fig = px.line(daily_cum_returns, title=title)
35
  return fig
36
 
37
- def plot_efficient_frontier_and_max_sharpe(mu, S):
38
- # ์ตœ๋Œ€ ์ƒคํ”„ ๋น„์œจ๋กœ ํฌํŠธํด๋ฆฌ์˜ค ์ตœ์ ํ™” ๋ฐ ํšจ์œจ์  ํˆฌ์ž์„  ๊ทธ๋ฆฌ๊ธฐ
39
- ef = EfficientFrontier(mu, S)
40
- fig, ax = plt.subplots(figsize=(6, 4))
41
- ef_max_sharpe = copy.deepcopy(ef)
42
- plotting.plot_efficient_frontier(ef, ax=ax, show_assets=False)
43
- ef_max_sharpe.max_sharpe(risk_free_rate=0.02)
44
- ret_tangent, std_tangent, _ = ef_max_sharpe.portfolio_performance()
45
- ax.scatter(std_tangent, ret_tangent, marker="*", s=100, c="r", label="Max Sharpe")
46
- ax.legend()
47
- return fig
48
-
49
- def plot_weights(weights):
50
- # ํฌํŠธํด๋ฆฌ์˜ค ์ตœ์  ํˆฌ์ž ๋น„์œจ ๊ทธ๋ž˜ํ”„ ์ถœ๋ ฅ
51
- labels = weights.keys()
52
- sizes = weights.values()
53
- fig, ax = plt.subplots()
54
- ax.pie(sizes, labels=labels, autopct='%1.1f%%')
55
- ax.axis('equal')
56
- return fig
57
  def output_results(start_date, end_date, tickers_string):
58
  tickers = tickers_string.split(',')
59
  stocks_df = yf.download(tickers, start=start_date, end=end_date)['Adj Close']
60
-
61
- tickers_info = {}
62
- news_data = {}
63
- for ticker in tickers:
64
- ticker_obj = yf.Ticker(ticker)
65
- tickers_info[ticker] = ticker_obj.info
66
- news_data[ticker] = ticker_obj.news
67
-
68
- # ๊ฒฐ๊ณผ ๋ฐ์ดํ„ฐ ์ƒ์„ฑ
69
- fig_indiv_prices = px.line(stocks_df, title='๊ฐœ๋ณ„ ์ฃผ์‹ ๊ฐ€๊ฒฉ')
70
- daily_returns = stocks_df.pct_change(fill_method=None).dropna()
71
- daily_cum_returns = (1 + daily_returns).cumprod() * 1000
72
- fig_cum_returns = px.line(daily_cum_returns, title='๊ฐœ๋ณ„ ์ฃผ์‹์˜ ๋ˆ„์  ์ˆ˜์ต๋ฅ  ($1,000 ์‹œ์ž‘)')
73
- corr_df = stocks_df.corr().round(2)
74
- fig_corr = px.imshow(corr_df, text_auto=True, title='์ฃผ์‹ ๊ฐ„ ์ƒ๊ด€ ๊ด€๊ณ„')
75
-
76
  mu = expected_returns.mean_historical_return(stocks_df)
77
  S = risk_models.sample_cov(stocks_df)
78
- ef = EfficientFrontier(mu, S)
79
- weights = ef.max_sharpe(risk_free_rate=0.02)
80
- cleaned_weights = ef.clean_weights()
81
- fig_weights = plot_weights(cleaned_weights)
82
- expected_annual_return, annual_volatility, sharpe_ratio = ef.portfolio_performance()
83
- fig_efficient_frontier = plot_efficient_frontier_and_max_sharpe(mu, S)
84
-
85
- # ํ‹ฐ์ปค ์ •๋ณด์™€ ๋‰ด์Šค๋ฅผ ํ•˜๋‚˜์˜ ๋ฌธ์ž์—ด๋กœ ์กฐํ•ฉ
86
- ticker_info_output = "\n\n".join([
87
- f"{ticker} ({tickers_info[ticker].get('longName', 'N/A')}, {tickers_info[ticker].get('sector', '์ •๋ณด ์—†์Œ')})\n" +
88
- "\n".join([f"๋‰ด์Šค: {news['title']} - {news['link']}" for news in news_data[ticker][:3]])
89
- for ticker in tickers
90
- ])
91
 
92
- return fig_cum_returns, fig_efficient_frontier, fig_corr, fig_indiv_prices, fig_weights, \
93
- f"{expected_annual_return*100:.2f}%", f"{annual_volatility*100:.2f}%", f"{sharpe_ratio:.2f}", ticker_info_output
94
 
 
 
 
 
 
 
 
 
 
95
 
96
- css = """footer { visibility: hidden; }"""
97
-
98
- with gr.Blocks(css=css) as app:
99
- gr.Markdown("""
100
- <style>
101
- .markdown-text h2 {
102
- font-size: 18px; # ํฐํŠธ ํฌ๊ธฐ๋ฅผ 18px๋กœ ์„ค์ •
103
- }
104
- </style>
105
- <h2>AIQ ์ž์‚ฐ ํฌํŠธํด๋ฆฌ์˜ค: ๊ธ€๋กœ๋ฒŒ ์ž์‚ฐ(์ฃผ์‹, ์ง€์ˆ˜, BTC, ์ƒํ’ˆ ๋“ฑ) AI ํฌํŠธํด๋ฆฌ์˜ค ์ตœ์ ํ™” ์„œ๋น„์Šค</h2>
106
- <h2>์ „์„ธ๊ณ„ ๋ชจ๋“  ํ‹ฐ์ปค ๋ณด๊ธฐ(์•ผํ›„ ํŒŒ์ด๋‚ธ์Šค): <a href="https://finance.yahoo.com/most-active" target="_blank">์—ฌ๊ธฐ๋ฅผ ํด๋ฆญ</a></h2>
107
- """)
108
- with gr.Tabs():
109
- with gr.TabItem("Portfolio Analysis"):
110
- with gr.Row():
111
- start_date = gr.Textbox("2013-01-01", label="์‹œ์ž‘ ์ผ์ž")
112
- end_date = gr.Textbox(datetime.now().date(), label="์ข…๋ฃŒ ์ผ์ž")
113
- tickers_string = gr.Textbox("NVDA,^GSPC,GC=F,MSFT,BTC-USD", label="์ฃผ์‹ ํ‹ฐ์ปค๋ฅผ ์‰ผํ‘œ๋กœ ๊ตฌ๋ถ„ํ•˜์—ฌ ์ž…๋ ฅํ•˜์„ธ์š”")
114
- btn = gr.Button("ํฌํŠธํด๋ฆฌ์˜ค ์ตœ์ ํ™” ๊ฒฐ๊ณผ ๋ณด๊ธฐ")
115
- with gr.Row():
116
- expected_annual_return = gr.Text(label="์˜ˆ์ƒ ์—ฐ๊ฐ„ ์ˆ˜์ต๋ฅ ")
117
- annual_volatility = gr.Text(label="์—ฐ๊ฐ„ ๋ณ€๋™์„ฑ")
118
- sharpe_ratio = gr.Text(label="์ƒคํ”„ ๋น„์œจ")
119
- with gr.Column():
120
- fig_cum_returns = gr.Plot(label="์ตœ์ ํ™”๋œ ํฌํŠธํด๋ฆฌ์˜ค์˜ ๋ˆ„์  ์ˆ˜์ต๋ฅ  (์‹œ์ž‘ ๊ฐ€๊ฒฉ $1,000)")
121
- fig_efficient_frontier = gr.Plot(label="ํšจ์œจ์  ํˆฌ์ž์„ ")
122
- fig_corr = gr.Plot(label="์ฃผ์‹ ๊ฐ„ ์ƒ๊ด€ ๊ด€๊ณ„")
123
- fig_indiv_prices = gr.Plot(label="๊ฐœ๋ณ„ ์ฃผ์‹ ๊ฐ€๊ฒฉ")
124
- fig_weights = gr.Plot(label="ํฌํŠธํด๋ฆฌ์˜ค ์ตœ์  ํˆฌ์ž ๋น„์œจ")
125
- ticker_info_output = gr.Textbox(label="ํ‹ฐ์ปค ์ •๋ณด ๋ฐ ๋‰ด์Šค")
126
- btn.click(fn=output_results, inputs=[start_date, end_date, tickers_string], outputs=[fig_cum_returns, fig_efficient_frontier, fig_corr, fig_indiv_prices, fig_weights, expected_annual_return, annual_volatility, sharpe_ratio, ticker_info_output])
127
-
128
- with gr.TabItem("Future Price Forecast"):
129
- with gr.Column():
130
- ticker_input = gr.Textbox(value="AAPL", label="Enter Stock Ticker for Forecast")
131
- forecast_button = gr.Button("Generate Forecast")
132
- forecast_chart = gr.Plot(label="Forecast Chart")
133
- forecast_data = gr.Dataframe()
134
- forecast_button.click(fn=predict_future_prices, inputs=[ticker_input], outputs=[forecast_chart, forecast_data])
135
-
136
- app.launch()
 
1
  import gradio as gr
2
  import yfinance as yf
3
+ from pypfopt import EfficientFrontier, risk_models, expected_returns
 
 
 
 
 
 
4
  import pandas as pd
5
+ import plotly.graph_objects as go
 
6
  from datetime import datetime
 
7
 
8
+ def plot_efficient_frontier_custom(mu, S):
9
+ ef = EfficientFrontier(mu, S)
10
+ fig = go.Figure()
 
 
 
11
 
12
+ # ํšจ์œจ์  ํˆฌ์ž์„  ๊ทธ๋ฆฌ๊ธฐ
13
+ weights = ef.efficient_frontier()
14
+ rets, stds = [], []
15
+ for weight in weights:
16
+ ef.set_weights(weight)
17
+ performance = ef.portfolio_performance()
18
+ rets.append(performance[0])
19
+ stds.append(performance[1])
20
+ fig.add_trace(go.Scatter(x=stds, y=rets, mode='lines', name='Efficient Frontier'))
21
+
22
+ # ์ตœ๋Œ€ ์ƒคํ”„ ๋น„์œจ ํฌ์ธํŠธ
23
+ ef.max_sharpe()
24
+ ret_sharpe, std_sharpe, _ = ef.portfolio_performance()
25
+ fig.add_trace(go.Scatter(x=[std_sharpe], y=[ret_sharpe], mode='markers', marker=dict(color='red', size=14), name='Max Sharpe Ratio'))
26
 
27
+ fig.update_layout(title='Efficient Frontier Plot', xaxis_title='Standard Deviation', yaxis_title='Return', legend_title='Legend')
 
 
 
 
 
 
 
 
28
  return fig
29
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
30
  def output_results(start_date, end_date, tickers_string):
31
  tickers = tickers_string.split(',')
32
  stocks_df = yf.download(tickers, start=start_date, end=end_date)['Adj Close']
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
33
  mu = expected_returns.mean_historical_return(stocks_df)
34
  S = risk_models.sample_cov(stocks_df)
 
 
 
 
 
 
 
 
 
 
 
 
 
35
 
36
+ fig_efficient_frontier = plot_efficient_frontier_custom(mu, S)
37
+ return fig_efficient_frontier
38
 
39
+ with gr.Blocks() as app:
40
+ with gr.Row():
41
+ start_date = gr.Textbox("2013-01-01", label="Start Date")
42
+ end_date = gr.Textbox(datetime.now().date(), label="End Date")
43
+ tickers_string = gr.Textbox("AAPL, MSFT, AMZN", label="Enter tickers separated by comma")
44
+ btn = gr.Button("Show Efficient Frontier")
45
+
46
+ fig_efficient_frontier = gr.Plot(label="Efficient Frontier")
47
+ btn.click(fn=output_results, inputs=[start_date, end_date, tickers_string], outputs=fig_efficient_frontier)
48
 
49
+ app.launch()