Spaces:
Paused
Paused
Update ml_engine/titan_engine.py
Browse files- ml_engine/titan_engine.py +19 -18
ml_engine/titan_engine.py
CHANGED
|
@@ -1,5 +1,5 @@
|
|
| 1 |
# ml_engine/titan_engine.py
|
| 2 |
-
# (V1.
|
| 3 |
|
| 4 |
import os
|
| 5 |
import joblib
|
|
@@ -115,15 +115,15 @@ class TitanEngine:
|
|
| 115 |
df['Trend_Strong'] = 0
|
| 116 |
|
| 117 |
except Exception as e:
|
| 118 |
-
print(f"⚠️ [Titan Warning] Error calculating indicators for {tf}: {e}")
|
| 119 |
# في حال حدوث خطأ، نترك الأعمدة كما هي (ستكون NaN إذا لم يتم إنشاؤها)
|
|
|
|
| 120 |
|
| 121 |
return df.reset_index(drop=True)
|
| 122 |
|
| 123 |
def predict(self, ohlcv_data: dict) -> dict:
|
| 124 |
"""
|
| 125 |
-
استقبال البيانات الخام
|
| 126 |
-
تجهيزها، ثم استدعاء النموذج للتنبؤ.
|
| 127 |
"""
|
| 128 |
if not self.initialized or not self.model:
|
| 129 |
return {'score': 0.0, 'error': 'Titan not initialized'}
|
|
@@ -141,47 +141,48 @@ class TitanEngine:
|
|
| 141 |
|
| 142 |
if df.empty: continue
|
| 143 |
|
| 144 |
-
# تطبيق المؤشرات حسب الإطار
|
| 145 |
df = self.apply_inverted_pyramid(df, tf)
|
| 146 |
processed_tfs[tf] = df
|
| 147 |
|
| 148 |
-
# 2. الدمج (Alignment)
|
| 149 |
if '5m' not in processed_tfs or processed_tfs['5m'].empty:
|
| 150 |
return {'score': 0.0, 'error': 'Missing 5m base timeframe'}
|
| 151 |
|
| 152 |
-
# نأخذ آخر صف فقط من الـ 5m كأساس
|
| 153 |
latest_5m = processed_tfs['5m'].iloc[-1:].copy()
|
| 154 |
latest_ts = latest_5m['timestamp'].iloc[0]
|
| 155 |
|
| 156 |
base_row = latest_5m.add_prefix('5m_').rename(columns={'5m_timestamp': 'timestamp'})
|
| 157 |
|
| 158 |
-
# دمج باقي الأطر
|
| 159 |
for tf, df in processed_tfs.items():
|
| 160 |
if tf == '5m' or df.empty: continue
|
| 161 |
-
# العثور على الشمعة المناسبة زمنياً
|
| 162 |
relevant_row = df[df['timestamp'] <= latest_ts].iloc[-1:].copy()
|
| 163 |
if relevant_row.empty: continue
|
| 164 |
|
| 165 |
-
# تجهيز الأعمدة للدمج
|
| 166 |
cols = [c for c in relevant_row.columns if c not in ['timestamp','open','high','low','close','volume']]
|
| 167 |
for col in cols:
|
| 168 |
base_row[f"{tf}_{col}"] = relevant_row[col].values[0]
|
| 169 |
|
| 170 |
-
# 3. تجهيز شعاع الإدخال (Feature Vector)
|
| 171 |
-
# التأكد من وجود كل الميزات المطلوبة بالترتيب الصحيح
|
| 172 |
input_data = []
|
| 173 |
for feat in self.feature_names:
|
| 174 |
val = base_row.get(feat, np.nan)
|
| 175 |
-
|
| 176 |
if isinstance(val, (pd.Series, np.ndarray)):
|
| 177 |
val = val.iloc[0] if len(val) > 0 else np.nan
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 178 |
input_data.append(val)
|
| 179 |
|
| 180 |
# 4. التنبؤ
|
| 181 |
-
# تحويل إلى DMatrix
|
| 182 |
-
# نستخدم np.nan القيم المفقودة ليقوم XGBoost بمعالجتها تلقائياً
|
| 183 |
dtest = xgb.DMatrix([input_data], feature_names=self.feature_names, missing=np.nan)
|
| 184 |
-
prediction = self.model.predict(dtest)[0]
|
| 185 |
|
| 186 |
return {
|
| 187 |
'score': float(prediction),
|
|
@@ -190,6 +191,6 @@ class TitanEngine:
|
|
| 190 |
}
|
| 191 |
|
| 192 |
except Exception as e:
|
| 193 |
-
# print(f"
|
| 194 |
-
traceback.print_exc()
|
| 195 |
return {'score': 0.0, 'error': str(e)}
|
|
|
|
| 1 |
# ml_engine/titan_engine.py
|
| 2 |
+
# (V1.2 - Titan Inference Engine - Infinity Safety Patch)
|
| 3 |
|
| 4 |
import os
|
| 5 |
import joblib
|
|
|
|
| 115 |
df['Trend_Strong'] = 0
|
| 116 |
|
| 117 |
except Exception as e:
|
| 118 |
+
# print(f"⚠️ [Titan Warning] Error calculating indicators for {tf}: {e}")
|
| 119 |
# في حال حدوث خطأ، نترك الأعمدة كما هي (ستكون NaN إذا لم يتم إنشاؤها)
|
| 120 |
+
pass
|
| 121 |
|
| 122 |
return df.reset_index(drop=True)
|
| 123 |
|
| 124 |
def predict(self, ohlcv_data: dict) -> dict:
|
| 125 |
"""
|
| 126 |
+
استقبال البيانات الخام، تجهيزها، ثم استدعاء النموذج للتنبؤ.
|
|
|
|
| 127 |
"""
|
| 128 |
if not self.initialized or not self.model:
|
| 129 |
return {'score': 0.0, 'error': 'Titan not initialized'}
|
|
|
|
| 141 |
|
| 142 |
if df.empty: continue
|
| 143 |
|
| 144 |
+
# تطبيق المؤشرات حسب الإطار
|
| 145 |
df = self.apply_inverted_pyramid(df, tf)
|
| 146 |
processed_tfs[tf] = df
|
| 147 |
|
| 148 |
+
# 2. الدمج (Alignment)
|
| 149 |
if '5m' not in processed_tfs or processed_tfs['5m'].empty:
|
| 150 |
return {'score': 0.0, 'error': 'Missing 5m base timeframe'}
|
| 151 |
|
|
|
|
| 152 |
latest_5m = processed_tfs['5m'].iloc[-1:].copy()
|
| 153 |
latest_ts = latest_5m['timestamp'].iloc[0]
|
| 154 |
|
| 155 |
base_row = latest_5m.add_prefix('5m_').rename(columns={'5m_timestamp': 'timestamp'})
|
| 156 |
|
| 157 |
+
# دمج باقي الأطر
|
| 158 |
for tf, df in processed_tfs.items():
|
| 159 |
if tf == '5m' or df.empty: continue
|
|
|
|
| 160 |
relevant_row = df[df['timestamp'] <= latest_ts].iloc[-1:].copy()
|
| 161 |
if relevant_row.empty: continue
|
| 162 |
|
|
|
|
| 163 |
cols = [c for c in relevant_row.columns if c not in ['timestamp','open','high','low','close','volume']]
|
| 164 |
for col in cols:
|
| 165 |
base_row[f"{tf}_{col}"] = relevant_row[col].values[0]
|
| 166 |
|
| 167 |
+
# 3. تجهيز شعاع الإدخال (Feature Vector) مع التنظيف
|
|
|
|
| 168 |
input_data = []
|
| 169 |
for feat in self.feature_names:
|
| 170 |
val = base_row.get(feat, np.nan)
|
| 171 |
+
|
| 172 |
if isinstance(val, (pd.Series, np.ndarray)):
|
| 173 |
val = val.iloc[0] if len(val) > 0 else np.nan
|
| 174 |
+
|
| 175 |
+
# 🛡️ [CRITICAL FIX] تنظيف القيم اللانهائية (Inf)
|
| 176 |
+
# XGBoost ينهار إذا وجد inf، لذلك نحولها إلى nan
|
| 177 |
+
if np.isinf(val):
|
| 178 |
+
val = np.nan
|
| 179 |
+
|
| 180 |
input_data.append(val)
|
| 181 |
|
| 182 |
# 4. التنبؤ
|
| 183 |
+
# تحويل إلى DMatrix
|
|
|
|
| 184 |
dtest = xgb.DMatrix([input_data], feature_names=self.feature_names, missing=np.nan)
|
| 185 |
+
prediction = self.model.predict(dtest)[0]
|
| 186 |
|
| 187 |
return {
|
| 188 |
'score': float(prediction),
|
|
|
|
| 191 |
}
|
| 192 |
|
| 193 |
except Exception as e:
|
| 194 |
+
# print(f"❌ [Titan Error] {e}")
|
| 195 |
+
# traceback.print_exc()
|
| 196 |
return {'score': 0.0, 'error': str(e)}
|