import streamlit as st import yfinance as yf import pandas as pd import timesfm import os from datetime import date, timedelta, datetime import pytz os.environ['XLA_PYTHON_CLIENT_PREALLOCATE'] = 'false' st.set_page_config(page_title="Google TimesFM Zaman Serisi Tahmini", layout="wide") st.title("📈 Google TimesFM Zaman Serisi Tahmini") st.markdown("Google Research tarafından geliştirilen model ile hisse senedi tahmini.") with st.sidebar: ticker = st.text_input("Hisse Sembolü (Örn: AAPL veya THYAO.IS)", "AAPL") feature = st.selectbox("Tahmin Değişkeni", ["Close", "Open", "High", "Low", "Volume"]) start_date_str = st.text_input("Başlangıç Tarihi (YYYY-MM-DD)", "2000-01-01") end_date_str = st.text_input("Bitiş Tarihi (YYYY-MM-DD)", str(date.today() - timedelta(days=1))) try: start_date = date.fromisoformat(start_date_str) end_date = date.fromisoformat(end_date_str) except ValueError: st.error("Tarih formatı hatalı. YYYY-MM-DD kullanın.") st.stop() @st.cache_data def load_data(symbol, start, end): df = yf.download(symbol, start=start, end=end + timedelta(days=1)) return df @st.cache_data def load_next_day(symbol, end): df = yf.download(symbol, start=end + timedelta(days=1), end=end + timedelta(days=6)) return df if start_date >= end_date: st.warning("Başlangıç tarihi bitiş tarihinden önce olmalı.") else: data = load_data(ticker, start_date, end_date) if not data.empty: st.subheader(f"{ticker} - {start_date} / {end_date} Grafiği") st.line_chart(data[feature]) if st.button("Sonraki Günü Tahmin Et"): with st.spinner("TimesFM Modeli Çalışıyor..."): try: tfm = timesfm.TimesFm( hparams=timesfm.TimesFmHparams( context_len=512, horizon_len=1, input_patch_len=32, output_patch_len=128, num_layers=20, model_dims=1280, backend="cpu" ), checkpoint=timesfm.TimesFmCheckpoint( huggingface_repo_id="google/timesfm-1.0-200m-pytorch" ) ) last_value = data[feature].values.flatten()[-1] input_data = data[feature].values.flatten() forecast, _ = tfm.forecast(inputs=[input_data], freq=[0]) predicted = forecast[0][0] pred_yon = "📈 Yükseliş" if predicted > last_value else "📉 Düşüş" st.success(f"Tahmin: {end_date + timedelta(days=1)} günü {feature} → **{predicted:.2f}** — {pred_yon}") target_date = end_date + timedelta(days=1) # Piyasa kapanış saati kontrolü is_turkish = ticker.upper().endswith(".IS") if is_turkish: tz = pytz.timezone("Europe/Istanbul") market_close_hour = 18 else: tz = pytz.timezone("America/New_York") market_close_hour = 16 now_local = datetime.now(tz) market_closed = ( target_date < date.today() or (target_date == date.today() and now_local.hour >= market_close_hour) ) if market_closed: actual_data = load_next_day(ticker, end_date) if not actual_data.empty: actual_date = actual_data.index[0].date() actual = actual_data[feature].values.flatten()[0] fark = actual - predicted actual_yon = "📈 Yükseliş" if actual > last_value else "📉 Düşüş" dogru = "✅ Doğru Tahmin" if pred_yon == actual_yon else "❌ Yanlış Tahmin" st.info(f"Gerçek Değer ({actual_date}): **{actual:.2f}** | Fark: **{fark:+.2f}** ({fark/actual*100:+.2f}%) — {actual_yon} — {dogru}") else: st.info("Gerçek değer bulunamadı (tatil veya veri yok).") else: st.info(f"{target_date} piyasası henüz kapanmadı — gerçek değer gösterilemiyor.") except Exception as e: st.error(f"Tahmin sırasında bir hata oluştu: {e}") else: st.warning("Veri bulunamadı, lütfen sembolü kontrol edin.")