Алексей Боровков – Алгоритмический трейдинг: Создание, тестирование и запуск роботов на рынке Форекс (страница 6)
# 2. КЛАСС ДЛЯ ОПТИМИЗАЦИИ ПАРАМЕТРОВ
# =====================================================================
class TrendFollowerOptimizer(bt.Strategy):
"""Версия стратегии для оптимизации параметров"""
params = (
('fast_ma', 50),
('slow_ma', 200),
('adx_threshold', 25),
('risk_per_trade', 0.01),
)
def __init__(self):
self.fast_ma = bt.indicators.SMA(self.data.close, period=self.p.fast_ma)
self.slow_ma = bt.indicators.SMA(self.data.close, period=self.p.slow_ma)
self.adx = bt.indicators.ADX(self.data, period=14)
self.order = None
def next(self):
if self.order:
return
if not self.position:
if (self.fast_ma[-1] < self.slow_ma[-1] and
self.fast_ma[0] > self.slow_ma[0] and
self.adx[0] > self.p.adx_threshold):
size = self.broker.getvalue() * self.p.risk_per_trade / self.data.close[0]
self.order = self.buy(size=size)
else:
if self.fast_ma[-1] > self.slow_ma[-1] and self.fast_ma[0] < self.slow_ma[0]:
self.order = self.close()
# =====================================================================
# 3. ФУНКЦИИ ДЛЯ ТЕСТИРОВАНИЯ И АНАЛИЗА
# =====================================================================
def download_data(symbol='EURUSD=X', start_date='2020-01-01', end_date='2023-12-31'):
"""Загрузка данных с Yahoo Finance"""
print(f"Загрузка данных для {symbol}…")
data = yf.download(symbol, start=start_date, end=end_date, progress=False)
# Преобразуем индексы для backtrader
data.index = pd.to_datetime(data.index)
data = data[['Open', 'High', 'Low', 'Close', 'Volume']]
return data
def run_backtest(data, initial_cash=10000, commission=0.001, **strategy_params):
"""Запуск бэктеста"""
cerebro = bt.Cerebro()
# Добавляем данные
data_feed = bt.feeds.PandasData(dataname=data)
cerebro.adddata(data_feed)
# Добавляем стратегию
cerebro.addstrategy(TrendFollowerStrategy, **strategy_params)
# Настройки брокера
cerebro.broker.setcash(initial_cash)
cerebro.broker.setcommission(commission=commission)
# Добавляем анализаторы
cerebro.addanalyzer(btanalyzers.Returns, _name='returns')
cerebro.addanalyzer(btanalyzers.SharpeRatio, _name='sharpe', riskfreerate=0.0)
cerebro.addanalyzer(btanalyzers.DrawDown, _name='drawdown')
cerebro.addanalyzer(btanalyzers.TradeAnalyzer, _name='trades')
cerebro.addanalyzer(btanalyzers.SQN, _name='sqn')
print(f'Начальный капитал: {initial_cash:.2f}')
print(f'Комиссия: {commission*100:.2f}%')
# Запуск
results = cerebro.run()
strat = results[0]
# Вывод результатов
print('\n' + '='*50)
print('РЕЗУЛЬТАТЫ БЭКТЕСТА')
print('='*50)
final_value = cerebro.broker.getvalue()