import yfinance as yf import streamlit as st import pandas as pd import requests st.title("So sánh Outperform / Underperform theo Sector") symbols_input = st.text_input("Nhập mã cổ phiếu (cách nhau bằng dấu phẩy, ví dụ: HIMS,AAPL,TSLA):") period = st.selectbox("Chọn khoảng thời gian so sánh:", ['5d', '1mo', '3mo', '6mo']) # Tự động dò ETF theo sector dựa trên yfinance sector_to_etf = { 'Technology': 'XLK', 'Health Care': 'XLV', 'Financial Services': 'XLF', 'Consumer Cyclical': 'XLY', 'Energy': 'XLE', 'Industrials': 'XLI', 'Consumer Defensive': 'XLP', 'Utilities': 'XLU', 'Materials': 'XLB', 'Real Estate': 'XLRE', 'Communication Services': 'XLC' } def get_sector_etf(symbol): try: ticker = yf.Ticker(symbol) info = ticker.info sector = info.get("sector", None) etf = sector_to_etf.get(sector, None) return sector, etf except: return None, None if symbols_input: symbols = [s.strip().upper() for s in symbols_input.split(",")] results = [] for symbol in symbols: sector, etf = get_sector_etf(symbol) if not etf: results.append({"Symbol": symbol, "Sector ETF": "Không rõ", "Kết luận": "Không phân tích được"}) continue stock_data = yf.download(symbol, period=period)['Close'] etf_data = yf.download(etf, period=period)['Close'] if stock_data is None or stock_data.empty or etf_data is None or etf_data.empty: results.append({"Symbol": symbol, "Sector ETF": etf, "Kết luận": "Không có dữ liệu"}) continue if len(stock_data) >= 2 and len(etf_data) >= 2: pct_stock = float((stock_data.iloc[-1] - stock_data.iloc[0]) / stock_data.iloc[0] * 100) pct_sector = float((etf_data.iloc[-1] - etf_data.iloc[0]) / etf_data.iloc[0] * 100) verdict = "Outperform" if pct_stock > pct_sector else "Underperform" results.append({ "Symbol": symbol, "Sector ETF": etf, "% Stock": f"{pct_stock:.2f}%", "% Sector": f"{pct_sector:.2f}%", "Kết luận": verdict }) else: results.append({"Symbol": symbol, "Sector ETF": etf, "Kết luận": "Dữ liệu không đủ"}) df = pd.DataFrame(results) st.dataframe(df)