Отвечаю на критику: бэктест линейной регрессии (из S&C 2007 года) на фьючерсах MOEX в 2025. Код и результаты!
Последние две недели я публиковал подборки из рубрики Traders’ Tips журнала Technical Analysis of STOCKS & COMMODITIES за 2001-2005 и 2006-2010 годы. Спасибо за ваши комментарии — от ироничных “опять комиксы?” до вполне серьёзных вопросов о практическом применении и бэктестах. Именно они побудили меня подойти к делу иначе. Подборка систем и индикаторов за 2006-2010 одного старейшего журнала по техническому анализу Вместо очередного обзора я решил сосредоточиться на одной идее: реализовать её на Pine Script для TradingView и протестировать на фьючерсах с Московской Биржи. Кстати, Traders’ Tips — это не отдельное приложение, а рубрика в журнале. Но суть не в этом: её практическая ценность по-прежнему велика. Лучшие системы и индикаторы 2001–2005: подборка из архива классического издания по теханализу В центре внимания — случайно выбранная статья Барбары Стар “Confirming Price Trend” (S&C, декабрь 2007). Почему именно она? Подтверждение тренда остаётся актуальной задачей, а методы вроде линейной регрессии и R² доступны для понимания и применимы на дневных и часовых графиках. В статье — теория этой стратегии, код на Pine Script, результаты тестирования и выводы. Маленький кусок статьи. Легально тут Что такое линейная регрессия и R-squared: простыми словамиПредставьте, что вы едете по дороге. Линейная регрессия — это как прямая трасса, проведённая по данным: она показывает общий курс, игнорируя кочки и повороты. Цена движется вокруг этой «дороги», а наклон линии подсказывает, в какую сторону едем — вверх или вниз.Теперь про R-squared: это как индикатор сигнала Wi-Fi. Если он близок к 1 — цена чётко держится вдоль регрессии, тренд сильный. Если ближе к нулю — «связь» теряется, рынок шумный, направление неясное.Маленький кусок статьи. Легально тут Почему это круче скользящих средних? У регрессии меньше запаздываний и она точнее «схватывает» развороты. А R-squared помогает не гадать — есть тренд или просто случайное движение. Вместе они дают простую, но мощную систему фильтрации шума и подтверждения тренда.Как использовать это в трейдингеНачнём с периода: 10 баров — для поиска коротких импульсов и ранних сигналов, 20 баров — сбалансированный вариант для дневных графиков, 50 баров — для фильтрации шума и работы по тренду. Выбор зависит от стиля торговли и таймфрейма.R-squared помогает определить фазу тренда:его рост с низких уровней (например, с 0.1 до 0.3) часто указывает на начало движения;падение с высоких (например, с 0.6 до 0.3) — признак ослабления и возможного флэта.Ориентиры:для 20 баров значим уровень 0.20;для 10: 0.40;для 50: достаточно 0.08.Наклон линии регрессии (slope) показывает направление:выше нуля — тренд вверх;ниже — вниз.Вместе с R² он позволяет отличить уверенное движение от случайного шума и избегать ложных входов. Бэктест: проверим идею на практикеИнструмент: TradingView и Pine ScriptДля реализации стратегии я выбрал TradingView. Это один из самых доступных инструментов для быстрого прототипирования торговых идей: открыл браузер, вставил код — и сразу увидел результат на графике. Особенно важно, что платформа не требует установки дополнительных библиотек, терминалов и настроек, как это часто бывает с Python или AmiBroker. Всё работает «из коробки», а язык Pine Script — простой и интуитивный, особенно если вы уже знакомы с техническим анализом.К тому же, код можно легко адаптировать и поделиться ссылкой на него, чтобы каждый мог протестировать его самостоятельно — даже без подписки на платные функции. У меня есть реферальная ссылка TradingView: если вы зарегистрируетесь по ней, это немного поддержит меня, а вам будет всё то же самое.Таймфреймы: дневной и часовойЯ протестировал стратегию на двух таймфреймах: дневном и часовом. Почему именно они?Дневной — наиболее стабилен и подходит для анализа крупных движений. Его удобно использовать и тем, кто торгует вручную и не хочет реагировать на каждое движение внутри дня.Часовой — даёт больше сигналов и позволяет точнее отследить динамику внутри тренда.Мне кажется что для частного трейдера эти два масштаба — оптимальный компромисс между частотой сигналов и управляемостью стратегии.Тестируемая логикаВ стратегии используются два ключевых фильтра: наклон линии линейной регрессии и значение R². Условия простые: входим в позицию, если цена «прорывает» линию регрессии, а R² превышает заданный порог и растёт. Выход из позиции осуществляется по трейлинг-стопу, значение которого задаётся в процентах от экстремума.Представленный код — моя интерпретация идеи из статьи Барбары Стар. Он может отличаться от оригинального примера из журнала, но отражает основную логику и добавляет реалистичные параметры торговли, включая комиссии и проскальзывание.Результаты: деньДля дневного графика я включил настройку «Корректировать с учётом изменений контрактов» — такая корректировка убирает ценовые разрывы между контрактами (гэпы), возникающие при переходе от одного фьючерса к другому.Торговля тремя контрактами фьючерсом на доллар/рубль (Si) на Мосбирже с ко

Последние две недели я публиковал подборки из рубрики Traders’ Tips журнала Technical Analysis of STOCKS & COMMODITIES за 2001-2005 и 2006-2010 годы. Спасибо за ваши комментарии — от ироничных “опять комиксы?” до вполне серьёзных вопросов о практическом применении и бэктестах. Именно они побудили меня подойти к делу иначе.
Подборка систем и индикаторов за 2006-2010 одного старейшего журнала по техническому анализу
Вместо очередного обзора я решил сосредоточиться на одной идее: реализовать её на Pine Script для TradingView и протестировать на фьючерсах с Московской Биржи. Кстати, Traders’ Tips — это не отдельное приложение, а рубрика в журнале. Но суть не в этом: её практическая ценность по-прежнему велика.
Лучшие системы и индикаторы 2001–2005: подборка из архива классического издания по теханализу
В центре внимания — случайно выбранная статья Барбары Стар “Confirming Price Trend” (S&C, декабрь 2007). Почему именно она? Подтверждение тренда остаётся актуальной задачей, а методы вроде линейной регрессии и R² доступны для понимания и применимы на дневных и часовых графиках.
В статье — теория этой стратегии, код на Pine Script, результаты тестирования и выводы.
Маленький кусок статьи. Легально тут
Что такое линейная регрессия и R-squared: простыми словами
Представьте, что вы едете по дороге. Линейная регрессия — это как прямая трасса, проведённая по данным: она показывает общий курс, игнорируя кочки и повороты. Цена движется вокруг этой «дороги», а наклон линии подсказывает, в какую сторону едем — вверх или вниз.
Теперь про R-squared: это как индикатор сигнала Wi-Fi. Если он близок к 1 — цена чётко держится вдоль регрессии, тренд сильный. Если ближе к нулю — «связь» теряется, рынок шумный, направление неясное.Маленький кусок статьи. Легально тут
Почему это круче скользящих средних? У регрессии меньше запаздываний и она точнее «схватывает» развороты. А R-squared помогает не гадать — есть тренд или просто случайное движение. Вместе они дают простую, но мощную систему фильтрации шума и подтверждения тренда.
Как использовать это в трейдинге
Начнём с периода: 10 баров — для поиска коротких импульсов и ранних сигналов, 20 баров — сбалансированный вариант для дневных графиков, 50 баров — для фильтрации шума и работы по тренду. Выбор зависит от стиля торговли и таймфрейма.
R-squared помогает определить фазу тренда:
его рост с низких уровней (например, с 0.1 до 0.3) часто указывает на начало движения;
падение с высоких (например, с 0.6 до 0.3) — признак ослабления и возможного флэта.
Ориентиры:
для 20 баров значим уровень 0.20;
для 10: 0.40;
для 50: достаточно 0.08.
Наклон линии регрессии (slope) показывает направление:
выше нуля — тренд вверх;
ниже — вниз.
Вместе с R² он позволяет отличить уверенное движение от случайного шума и избегать ложных входов.
Бэктест: проверим идею на практике
Инструмент: TradingView и Pine Script
Для реализации стратегии я выбрал TradingView. Это один из самых доступных инструментов для быстрого прототипирования торговых идей: открыл браузер, вставил код — и сразу увидел результат на графике. Особенно важно, что платформа не требует установки дополнительных библиотек, терминалов и настроек, как это часто бывает с Python или AmiBroker. Всё работает «из коробки», а язык Pine Script — простой и интуитивный, особенно если вы уже знакомы с техническим анализом.
К тому же, код можно легко адаптировать и поделиться ссылкой на него, чтобы каждый мог протестировать его самостоятельно — даже без подписки на платные функции. У меня есть реферальная ссылка TradingView: если вы зарегистрируетесь по ней, это немного поддержит меня, а вам будет всё то же самое.
Таймфреймы: дневной и часовой
Я протестировал стратегию на двух таймфреймах: дневном и часовом. Почему именно они?
Дневной — наиболее стабилен и подходит для анализа крупных движений. Его удобно использовать и тем, кто торгует вручную и не хочет реагировать на каждое движение внутри дня.
Часовой — даёт больше сигналов и позволяет точнее отследить динамику внутри тренда.
Мне кажется что для частного трейдера эти два масштаба — оптимальный компромисс между частотой сигналов и управляемостью стратегии.
Тестируемая логика
В стратегии используются два ключевых фильтра: наклон линии линейной регрессии и значение R². Условия простые: входим в позицию, если цена «прорывает» линию регрессии, а R² превышает заданный порог и растёт. Выход из позиции осуществляется по трейлинг-стопу, значение которого задаётся в процентах от экстремума.
Представленный код — моя интерпретация идеи из статьи Барбары Стар. Он может отличаться от оригинального примера из журнала, но отражает основную логику и добавляет реалистичные параметры торговли, включая комиссии и проскальзывание.
Результаты: день
Для дневного графика я включил настройку «Корректировать с учётом изменений контрактов» — такая корректировка убирает ценовые разрывы между контрактами (гэпы), возникающие при переходе от одного фьючерса к другому.
Торговля тремя контрактами фьючерсом на доллар/рубль (Si) на Мосбирже с комиссией 0.04% и проскальзыванием: Результаты: день
Результаты: час
На часовом таймфрейме стратегия охватила примерно полтора года котировок. Это позволяет увидеть, как система работает в разных фазах рынка: трендовых и боковых.
Торговля тремя контрактами фьючерсом на доллар/рубль (Si) на Мосбирже с комиссией 0.04% и проскальзыванием: Результаты: час
Код стратеги на Pine Script для TradingView

Верхняя панель — код стратегии:
//07.05.2025 // Стратегия на основе линейной регрессии и коэффициента детерминации R-squared // На основе https://traders.com/documentation/feedbk_docs/2007/12/Abstracts_new/Star/star.html // Михаил Шардин, https://shardin.name/?utm_source=tradingview //@version=6 strategy("Линейная регрессия + R² стратегия", overlay=true, commission_type=strategy.commission.percent, // Тип комиссии: процент commission_value=0.04, // Значение комиссии: 0.04% slippage=10, // Проскальзывание в тиках process_orders_on_close=true, default_qty_type=strategy.fixed, default_qty_value=3, initial_capital=500000) // Начальный капитал // === Входные параметры === // Параметры линейной регрессии src = input.source(hlcc4, title="Источник данных") len = input.int(defval=20, minval=1, title="Длина периода линейной регрессии") r_squared_threshold = input.float(0.2, title="Порог R-squared", step=0.01, minval=0) trailingStopOffset = input.float(3.9, "Отступ трейлинг-стопа (%)", step=0.1, minval=0.1) // Выбор таймфрейма для расчетов targetTimeframe = input.timeframe("", title="Таймфрейм для расчетов", tooltip="Укажите таймфрейм, на котором должны производиться расчеты") // === Расчеты линейной регрессии и R-squared === // Получаем данные с выбранного таймфрейма targetClose = request.security(syminfo.tickerid, targetTimeframe, src) // Расчет линии линейной регрессии lrc = ta.linreg(targetClose, len, 0) // Расчет коэффициента детерминации R-squared correlation_coeff = ta.correlation(targetClose, lrc, len) r_squared = math.pow(correlation_coeff, 2) // Обработка случая, когда стандартное отклонение источника равно нулю (все значения одинаковы) is_constant_src = ta.stdev(targetClose, len) == 0 r_squared_adjusted = is_constant_src ? 1.0 : r_squared // === Условия входа === // Условие для лонг: линия регрессии ниже цены закрытия и R² растет и выше порога long_condition = lrc < close and r_squared_adjusted > r_squared_adjusted[1] and r_squared_adjusted > r_squared_threshold // Условие для шорт: линия регрессии выше цены закрытия и R² растет и выше порога short_condition = lrc > close and r_squared_adjusted > r_squared_adjusted[1] and r_squared_adjusted > r_squared_threshold // === Трейлинг-стоп на основе процентного отступа === var float highestLongPrice = na var float lowestShortPrice = na var float trailingStopLong = na var float trailingStopShort = na // Флаг для блокировки новых сигналов при активной позиции var bool blockNewSignals = false // Обновляем трейлинг-стопы if (strategy.position_size > 0) // Если открыта длинная позиция highestLongPrice := na(highestLongPrice) ? close : math.max(highestLongPrice, close) trailingStopLong := highestLongPrice * (1 - trailingStopOffset / 100) blockNewSignals := true if (strategy.position_size < 0) // Если открыта короткая позиция lowestShortPrice := na(lowestShortPrice) ? close : math.min(lowestShortPrice, close) trailingStopShort := lowestShortPrice * (1 + trailingStopOffset / 100) blockNewSignals := true // Проверяем условия выхода if (strategy.position_size > 0 and close <= trailingStopLong) strategy.close("Лонг") highestLongPrice := na trailingStopLong := na blockNewSignals := false if (strategy.position_size < 0 and close >= trailingStopShort) strategy.close("Шорт") lowestShortPrice := na trailingStopShort := na blockNewSignals := false // === Открытие позиций (только если нет активной позиции) === if (long_condition and not blockNewSignals and strategy.position_size == 0) strategy.entry("Лонг", strategy.long) highestLongPrice := close trailingStopLong := close * (1 - trailingStopOffset / 100) blockNewSignals := true if (short_condition and not blockNewSignals and strategy.position_size == 0) strategy.entry("Шорт", strategy.short) lowestShortPrice := close trailingStopShort := close * (1 + trailingStopOffset / 100) blockNewSignals := true // === Отображение === // Отображение линии линейной регрессии plot(lrc, color = color.blue, title = "Линия линейной регрессии", style = plot.style_line, linewidth = 2) // Отображение трейлинг-стопов plot(strategy.position_size > 0 ? trailingStopLong : na, title="Лонг трейлинг-стоп", color=color.green, linewidth=2, style=plot.style_linebr) plot(strategy.position_size < 0 ? trailingStopShort : na, title="Шорт трейлинг-стоп", color=color.red, linewidth=2, style=plot.style_linebr) // Дополнительные информационные панели var table info = table.new(position.top_right, 3, 4, border_width=1) table.cell(info, 0, 0, "Linear Regression", bgcolor=color.new(color.blue, 90), text_color=color.white) table.cell(info, 0, 1, "Значение:", text_color=color.white) table.cell(info, 1, 1, str.tostring(lrc, "#.##"), text_color=color.white) table.cell(info, 0, 2, "R-squared:", text_color=color.white) table.cell(info, 1, 2, str.tostring(r_squared_adjusted, "#.####"), text_color=r_squared_adjusted > r_squared_threshold ? color.green : color.red) table.cell(info, 0, 3, "Сигнал:", text_color=color.white) table.cell(info, 1, 3, blockNewSignals ? "Заблокирован" : long_condition ? "ЛОНГ" : short_condition ? "ШОРТ" : "Нет сигнала", text_color=blockNewSignals ? color.yellow : long_condition ? color.green : short_condition ? color.red : color.white)
Нижняя панель — код индикатора:
// 07.05.2025 // Михаил Шардин, https://shardin.name/?utm_source=tradingview // На основе https://traders.com/documentation/feedbk_docs/2007/12/Abstracts_new/Star/star.html //@version=6 indicator(title="Коэффициент детерминации (R-squared)", shorttitle="R²", overlay=false, precision=4) // Настройки индикатора src = input.source(close, title="Источник данных") len = input.int(20, minval=2, title="Длина периода") // Для корреляции нужно минимум 2 точки // Выбор таймфрейма для расчетов targetTimeframe = input.timeframe("", title="Таймфрейм для расчетов", tooltip="Укажите таймфрейм, на котором должны производиться расчеты регрессии и R²") targetSrc = request.security(syminfo.tickerid, targetTimeframe, src, lookahead=barmerge.lookahead_on) // Расчет линии линейной регрессии (Ŷ - предсказанные значения) lrc = ta.linreg(targetSrc, len, 0) // Расчет коэффициента детерминации R-squared // R² = (Correlation(Y, Ŷ))² // Y - это targetSrc (фактические значения) // Ŷ - это lrc (предсказанные значения) correlation_coeff = ta.correlation(targetSrc, lrc, len) r_squared = math.pow(correlation_coeff, 2) // Обработка случая, когда стандартное отклонение источника равно нулю (все значения одинаковы) is_constant_src = ta.stdev(targetSrc, len) == 0 r_squared_adjusted = is_constant_src ? 1.0 : r_squared // Отображение R-squared на графике plot(r_squared_adjusted, color=color.new(color.blue, 0), title="R-squared", style=plot.style_line, linewidth=2) // Уровни для R-squared для лучшей визуальной интерпретации hline(1, "Идеальное соответствие", color.gray, linestyle=hline.style_dashed) hline(0.8, "Очень сильное", color.new(color.green, 50), linestyle=hline.style_dotted) hline(0.5, "Среднее", color.new(color.orange, 50), linestyle=hline.style_dotted) hline(0.2, "Слабое", color.new(color.red, 50), linestyle=hline.style_dotted) hline(0, "Нет соответствия", color.gray, linestyle=hline.style_dashed)
Выводы и личное мнение
Тест показал: линейная регрессия с R² действительно может стать эффективным фильтром и подтверждением тренда — особенно на умеренных и длинных периодах.
Важно понимать, что простота кода не гарантирует прибыль — параметры требуют подстройки под инструмент, а условия рынка — постоянного внимания.
Тем не менее, эта стратегия может служить хорошей основой или фильтром внутри более сложной торговой системы.