Spaces:
Paused
Paused
Update simulation_engine/virtual_exchange.py
Browse files
simulation_engine/virtual_exchange.py
CHANGED
|
@@ -1,5 +1,5 @@
|
|
| 1 |
# simulation_engine/virtual_exchange.py
|
| 2 |
-
#
|
| 3 |
|
| 4 |
from datetime import datetime
|
| 5 |
import uuid
|
|
@@ -9,15 +9,15 @@ class VirtualExchange:
|
|
| 9 |
self,
|
| 10 |
initial_balance=10.0,
|
| 11 |
fee_rate=0.001,
|
| 12 |
-
tp_pct=1.
|
| 13 |
sl_pct=0.8,
|
| 14 |
bar_ms=300_000, # 5m
|
| 15 |
-
cooldown_bars=
|
| 16 |
min_trade_usd=0.10,
|
| 17 |
-
position_fraction=0.
|
| 18 |
max_concurrent=1,
|
| 19 |
-
soft_time_stop_bars=12, #
|
| 20 |
-
hard_time_stop_bars=24, #
|
| 21 |
):
|
| 22 |
self.initial_balance = float(initial_balance)
|
| 23 |
self.balance = float(initial_balance)
|
|
@@ -92,11 +92,9 @@ class VirtualExchange:
|
|
| 92 |
else:
|
| 93 |
# 2) Time-based exits: soft then hard
|
| 94 |
if self.soft_time_stop_bars and age_bars >= self.soft_time_stop_bars:
|
| 95 |
-
# Soft rule: close at breakeven-or-better around 1h
|
| 96 |
if current_price >= entry:
|
| 97 |
closed_trade = self._close(symbol, current_price, timestamp, "SOFT_TIME_STOP")
|
| 98 |
if not closed_trade and self.hard_time_stop_bars and age_bars >= self.hard_time_stop_bars:
|
| 99 |
-
# Hard rule: force close by ~2h
|
| 100 |
closed_trade = self._close(symbol, current_price, timestamp, "HARD_TIME_STOP")
|
| 101 |
|
| 102 |
if closed_trade:
|
|
@@ -183,7 +181,7 @@ class VirtualExchange:
|
|
| 183 |
current_dd = (self.metrics["peak_balance"] - self.balance) / max(self.metrics["peak_balance"], 1e-9)
|
| 184 |
self.metrics["max_drawdown"] = max(self.metrics["max_drawdown"], current_dd)
|
| 185 |
|
| 186 |
-
#
|
| 187 |
if self.cooldown_bars and self.bar_ms:
|
| 188 |
self.cooldowns[symbol] = timestamp + self.cooldown_bars * self.bar_ms
|
| 189 |
else:
|
|
|
|
| 1 |
# simulation_engine/virtual_exchange.py
|
| 2 |
+
# V2.0 — Single-position engine with cooldown and soft/hard time-stops (≈1h / 2h)
|
| 3 |
|
| 4 |
from datetime import datetime
|
| 5 |
import uuid
|
|
|
|
| 9 |
self,
|
| 10 |
initial_balance=10.0,
|
| 11 |
fee_rate=0.001,
|
| 12 |
+
tp_pct=1.6,
|
| 13 |
sl_pct=0.8,
|
| 14 |
bar_ms=300_000, # 5m
|
| 15 |
+
cooldown_bars=1,
|
| 16 |
min_trade_usd=0.10,
|
| 17 |
+
position_fraction=0.45,
|
| 18 |
max_concurrent=1,
|
| 19 |
+
soft_time_stop_bars=12, # ~1h at 5m
|
| 20 |
+
hard_time_stop_bars=24, # ~2h at 5m
|
| 21 |
):
|
| 22 |
self.initial_balance = float(initial_balance)
|
| 23 |
self.balance = float(initial_balance)
|
|
|
|
| 92 |
else:
|
| 93 |
# 2) Time-based exits: soft then hard
|
| 94 |
if self.soft_time_stop_bars and age_bars >= self.soft_time_stop_bars:
|
|
|
|
| 95 |
if current_price >= entry:
|
| 96 |
closed_trade = self._close(symbol, current_price, timestamp, "SOFT_TIME_STOP")
|
| 97 |
if not closed_trade and self.hard_time_stop_bars and age_bars >= self.hard_time_stop_bars:
|
|
|
|
| 98 |
closed_trade = self._close(symbol, current_price, timestamp, "HARD_TIME_STOP")
|
| 99 |
|
| 100 |
if closed_trade:
|
|
|
|
| 181 |
current_dd = (self.metrics["peak_balance"] - self.balance) / max(self.metrics["peak_balance"], 1e-9)
|
| 182 |
self.metrics["max_drawdown"] = max(self.metrics["max_drawdown"], current_dd)
|
| 183 |
|
| 184 |
+
# تبريد لكل رمز
|
| 185 |
if self.cooldown_bars and self.bar_ms:
|
| 186 |
self.cooldowns[symbol] = timestamp + self.cooldown_bars * self.bar_ms
|
| 187 |
else:
|