Spaces:
Runtime error
Runtime error
| # Model deepseek-reasoner | |
| import backtrader as bt | |
| class TripleMACross(bt.Strategy): | |
| """ | |
| Triple moving average crossover strategy with 10% position sizing. | |
| - Entry: Fast SMA (5) crosses above Medium SMA (10) and Medium SMA is above Slow SMA (20) | |
| - Exit: Fast SMA crosses below Medium SMA OR Medium SMA crosses below Slow SMA | |
| - Position sizing: 10% of portfolio per trade | |
| """ | |
| params = ( | |
| ('fast_period', 5), | |
| ('medium_period', 10), | |
| ('slow_period', 20), | |
| ) | |
| def __init__(self): | |
| # Three moving averages | |
| self.sma_fast = bt.indicators.SMA(period=self.p.fast_period) | |
| self.sma_medium = bt.indicators.SMA(period=self.p.medium_period) | |
| self.sma_slow = bt.indicators.SMA(period=self.p.slow_period) | |
| # Crossover indicators | |
| self.cross_fast_medium = bt.indicators.CrossOver(self.sma_fast, self.sma_medium) | |
| self.cross_medium_slow = bt.indicators.CrossOver(self.sma_medium, self.sma_slow) | |
| # Track position for conditional logic | |
| self.position_open = False | |
| def next(self): | |
| # Entry condition: Fast crosses above Medium AND Medium > Slow (no existing position) | |
| if not self.position: | |
| if self.cross_fast_medium > 0 and self.sma_medium[0] > self.sma_slow[0]: | |
| self.buy(size=self.get_target_size()) # Use dynamic sizing | |
| self.position_open = True | |
| # Exit conditions: Fast crosses below Medium OR Medium crosses below Slow | |
| elif self.position_open: | |
| if self.cross_fast_medium < 0 or self.cross_medium_slow < 0: | |
| self.close() | |
| self.position_open = False | |
| def get_target_size(self): | |
| """Calculate 10% of current portfolio value""" | |
| return int((self.broker.getvalue() * 0.90) / self.data.close[0]) | |
| # Initialize Cerebro with strategy and sizer | |
| cerebro = bt.Cerebro() | |
| cerebro.addstrategy(TripleMACross, fast_period=5, medium_period=10, slow_period=20) |