uralpro
uralpro личный блог
17 июня 2015, 13:01

Как быстро увеличить производительность алгоритма. Часть 1

biasnn

Основные принципы увеличения прибыльности алгоритмов автоматизированной торговли изложены в блоге Inovancetech. Представляю здесь перевод этой статьи. В ней использованы некоторые алгоритмы и результаты цикла про машинное обучение (часть 1, часть 2).

После построения алгоритма, вам нужно убедиться, что он робастен и будет генерировать прибыльные сигналы при реальной торговле. В данном посте мы представим 3 легких способа увеличить производительность вашей модели.

Прежде чем улучшать модель, вы должны определить базовую производительность стратегии. Самый лучший способ сделать это — протестировать модель на новых исходных данных. Однако, вы всегда владеете довольно ограниченным набором данных, несмотря на их множество, предоставляемое финансовыми институтами. Значит, вы должны тщательно обдумать, как использовать имеющийся набор. По этим причинам, самое лучшее — разделить его на три отдельных части.

Тренировочный набор данных:

Это данные, которые вы используете для тренировки, или построения модели. Алгоритм будет пытаться найти взаимосвязь между входом ( вашими индикаторами) и выходом (где будет находится цена в следующем периоде — выше или ниже текущей). Обычно берут 60% имеющихся данных для этого набора.

Тестовый набор данных:

Мы будем использовать тестовый набор для определения производительности модели на данных, которые не использовались для тренировки. Этот набор мы применим для сравнения разных моделей ( или одной модели с разными параметрами),  необходимо, чтобы это был как можно более репрезентативный набор, учитывающий разные ситуации на рынках. Обычно, берут 20% от имеющихся данных для тестирования.

Проверочный набор данных:

Проверочные данные используются для определения, как хорошо наша окончательная модель будет работать на будущих периодах. Мы можем использовать данный набор единожды, как выборку «out-of sample», для избежания подгонок под эти последние данные. Если результат не соответствует требуемым показателям, вы должны использовать другой проверочный набор, чтобы убедиться в робастности модели. Последние 20% данных зарезервированы для проверочного набора.

1.Понимание вашей модели.

Перед тем, как улучшать модель, вам нужно понять характеристики данной модели, особенно — в каком случае возникает ее недооценка/подгонка под данные? Недооценка возникает, если алгоритм использует упрощенные предположения о состоянии рынка. Подгонка бывает, когда система подстраивается под шум, наличествующий в данных. Фокус в том, как определить, какое значение сигнала содержится в данных, без подгонки под случайный шум.

Быстрый способ узнать, где модель попадает под недооценку/подгонку, это сравнение ошибки тренировочного набора с ошибкой тестового набора данных. Если у вас большая ошибка в тренировочном и большая ошибка в тестовом наборе, вы с большой вероятностью имеете дело с недооценкой, а если вы получаете низкую величину ошибки в тренировочном наборе и высокою — в тестовом, то модель страдает от подгонки. В заглавии поста все это наглядно показано на графике.

Мы получили представление, когда наши модели подвержены недооценке/подгонке, далее рассмотрим другие способы улучшения алгоритмов.

2. Создание индикаторов.

Использование правильных входных данных для модели чрезвычайно важно. Выражение «мусор на входе — мусор на выходе» соответствует действительности, это означает, что если мы не подали значимой информации на вход алгоритма, то никогда не найдем в ней каких-либо паттернов или связей.

Если вы говорите «я использую 14-периодный RSI для торговли», за этими словами может скрываться больше, чем сказано. Вы можете применять наклон RSI, или его локальные максимумы и минимумы, расхождение с ценовым рядом, и множество других факторов. Однако модель получает только одну часть информации — текущее значение RSI. Для создания индикатора, или вычисления, основанного на значении RSI, нам нужно дать алгоритму  больше информации, чем просто одно значение.

Используем наивный байесовский алгоритм, более стабильный, чем другие, склонные к подгонке, для создания сложных индикаторов, могущих улучшить производительность. Используем программу на языке R, применение наивного байесовского классификатора подробно разбирается в части 2 цикла про машинное обучение.

Во-первых, инсталлируем нужные библиотеки, устанавливаем входные данные и вычисляем основные входные параметры:

install.packages(“quantmod”)
library(quantmod)
install.packages(“e1071”)
library(e1071)

startDate = as.Date("2009-01-01")
endDate = as.Date("2014-06-01")
#Установим диапазон дат, который хотим исследовать

getSymbols("MSFT", src = "yahoo", from = startDate, to = endDate)
#Получаем наши данные

EMA5<-EMA(Op(MSFT),5)
RSI14<-RSI(Op(MSFT),14)
Volume<-lag(MSFT[,5],1)
#Вычисляем основные индикаторы. Отметим: у нас есть лаг в данных по объему, так как мы используем вчерашние данные в качестве входных для избежания подгонки данных, так как мы вычисляем индикаторы из цен открытия

PriceChange<- Cl(MSFT) - Op(MSFT)
Class<-ifelse(PriceChange>0,"UP","DOWN")
#Создаем переменную, которую хотим предсказывать

BaselineDataSet<-data.frame(EMA5,RSI14,Volume)
BaselineDataSet<-round(BaselineDataSet,2)
#Округляем входные данные до двух знаков после запятой, для использовании байесовского алгоритма

BaselineDataSet<-data.frame(BaselineDataSet,Class)
BaselineDataSet<-BaselineDataSet[-c(1:14),]
colnames(BaselineDataSet)<-c("EMA5","RSI14","Volume","Class")
#Создаем набор данных, удаляя периоды вычисления индикаторов

BaselineTrainingSet<-BaselineDataSet[1:808,];BaselineTestSet< -BaselineDataSet[809:1077,];BaselineValSet<-BaselineDataSet[1078:1347,]
#Разделяем данные на 60% тренировочного набора, 20% тестового набора и 20% проверочного набора

Затем строим основную модель:

BaselineNB<-naiveBayes(Class~EMA5+RSI14+Volume,data=BaselineTrainingSet)

table(predict(BaselineNB,BaselineTestSet),BaselineTestSet[,4],dnn=list('predicted','actual')) 

nnnb

Получается не очень хорошо. Только 46% предсказаний верны, и у нас наблюдается недооценка, приводящая к большому числу предсказаний увеличения цены. Это серьезное доказательство того, что наша модель недостаточно сложна для обработки имеющихся входных данных.

Давайте создадим более сложные индикаторы и посмотрим, удастся ли уменьшить недооценку:

EMA5Cross<-EMA5-Op(MSFT)
RSI14ROC3<-ROC(RSI14,3,type="discrete")
VolumeROC1<-ROC(Volume,1,type="discrete")
#Исследуем расстояние между 5- периодной ЕМА и ценой открытия, и одно- и трехпериодный индикатор ROC на нашем индикаторе RSI  и объемах, соответственно

FeatureDataSet<-data.frame(EMA5Cross,RSI14ROC3,VolumeROC1)
FeatureDataSet<-round(FeatureDataSet,2)
#Округляем значение индикатора

FeatureDataSet<-data.frame(FeatureDataSet, Class)
FeatureDataSet<-FeatureDataSet[-c(1:17),]
colnames(FeatureDataSet)<-c("EMA5Cross","RSI14ROC3","VolumeROC1","Class")
#Создаем и называем набор данных

FeatureTrainingSet<-FeatureDataSet[1:806,]; FeatureTestSet< -FeatureDataSet[807:1075,]; FeatureValSet<-FeatureDataSet[1076:1344,]
#Создаем тренировочный, тестовы и проверочный наборы

И наконец, создаем нашу модель:

FeatureNB<-naiveBayes(Class~EMA5Cross+RSI14ROC3+VolumeROC1,data=FeatureTrainingSet)

Посмотрим, удалось ли уменьшить недооценку:

table(predict(FeatureNB,FeatureTestSet),FeatureTestSet[,4],dnn=list('predicted','actual')) 

nnnb1

У нас получилось увеличить аккуратность предсказания с 7% до 53% с использованием только относительно простых методов! Разберитесь как это произошло, просто наблюдайте за изменением этих индикаторов и переводите такие наблюдения в значения, которые понимает алгоритм, и вы сможете улучшить производительность стратегии еще больше.

В следующей статье мы разберем техники смешивания и форсирования, применяемые к множеству алгоритмов с целью улучшения производительности стратегии.

Другие стратегии, применяемые в алгоритмической торговле и биржевых роботах смотрите на моем сайте.

24 Комментария
  • anatolyutkin
    17 июня 2015, 13:09
    Что такое ошибка?
      • anatolyutkin
        17 июня 2015, 13:22
        uralpro, Но ведь торговый алгоритм--это достаточно хитрое предсказание. Как определить ошибку? Например, алго: при пересечении вверх SMA(10) входим лонг, при пересечении вниз выходим. Как для него определить ошибку?
    • Marcello
      17 июня 2015, 13:38
      uralpro, имеется ввиду, пошла ли цена вверх в ожидаемый (предсказываемый) период времени после пересечения?
    • anatolyutkin
      17 июня 2015, 14:11
      uralpro, То есть это процент прибыльных сделок что-ли? Но существуют прибыльные алгоритмы с этим процентом, меньшим 50. Они все недооценены?
        • anatolyutkin
          17 июня 2015, 14:34
          uralpro, У вас в тексте есть слова «большая ошибка». И не говорится, большая по сравнению с чем. Как понять фразу «Если у вас большая ошибка в тренировочном и большая ошибка в тестовом наборе, вы с большой вероятностью имеете дело с недооценкой,»?

          У меня есть роботы с угадайкой 40-50 процентов. Не понимаю, как автоматизация/ее отсутствие влияют на параметры алгоритма. Автоматизация--это вроде техническая вещь.
            • anatolyutkin
              17 июня 2015, 14:49
              uralpro, Это таймфреймовые трендовухи.
                • anatolyutkin
                  17 июня 2015, 15:36
                  uralpro, Их же много всяких разных. Ну пусть одна сделка раз в три дня.

                  Если честно, мне нравится концепция недооцененности/переподгонки. Нравится существование оптимума. Но хотелось бы деталей и конкретных примеров, потому что пока это выглядит лишь затравкой и не более. В качестве примера удобно взять что-то, имеющее смысл, но что не жалко. Поэтому я и предложил пересечения МА. Это простая трендовуха, эксплуатирует трендовость. Вот как понять--она переподогнана или недооценена?
                  • anatolyutkin
                    17 июня 2015, 15:39
                    anatolyutkin, Просто угадайка в качестве метрики, имхо, не пляшет. Просто в силу того, что не определяет финрез, а важен именно финрез.
                    • anatolyutkin
                      17 июня 2015, 16:07
                      uralpro, Есть и десяток сделок в день, но там угадайка, конечно, 50+%.

                      Простая/сложная--это слова. Имхо, есть то, что я называю край эджа. Пример: smart-lab.ru/blog/186186.php Это искусственный процесс. СБ, но с доп условием--смещено в контру при сильном отклонении. Вот код:

                      var: s(10),x(0);
                      x=2*Random(1)-1;
                      if s[1]-s[2]<-0.9 then x=x+0.8;
                      if s[1]-s[2]>0.9 then x=x-0.8;
                      s=s[1]+x;

                      И тут есть явный максимум эджа--0.8 средняя сделка и 90% угадайка. Все, что лучше--переподгонка, все, что хуже--недооценка.
                      Но тут процесс известен. На рынке--не так. И как понять, где край эджа? С опытом оно приходит, конечно, но может есть формальные способы находить оптимум?
                        • anatolyutkin
                          17 июня 2015, 18:32
                          uralpro, Это правильно, да. Ну теперь объясните еще, что такое большая/маленькая угадайка. Как понять фразу «Если у вас большая ошибка в тренировочном и большая ошибка в тестовом наборе, вы с большой вероятностью имеете дело с недооценкой,»?
                            • anatolyutkin
                              17 июня 2015, 18:59
                              uralpro,
                              1) Ну тут же распределение некое должно быть. Условно, если 30% на тренировочной и 30% на тестовой--это явная недоподгонка. Если 50 и 50--хз. Если 70 и 70--явная переподгонка.

                              2) Сами эти цифры (30, 70) зависят от системы. Мне известны системы с угадайкой 80+% при соотношении средний убыток/средний выигрыш=1:1. Но они не есть переподгонка, они просто юзают сильную неэффективность (это редкие события, конечно, частые события мне такие неизвестны). И наоборот, есть системы с частыми событиями и угадайкой 52-53% при win/loss=1:1. Их можно подточить до 55%, но это будет точно переподгонка, нарушающая их суть.
                              Зависимость правильных цифр от конкретной системы делает создание адекватной методы как минимум непростым, ибо не ясно, как формализовать что такое «конкретная система».
                                • anatolyutkin
                                  17 июня 2015, 19:16
                                  uralpro, Ну да, редким событиям вообще статистика не писана, так что ну их. А вот для высокочастотных можно попытаться оценить недо/переподгонку некими (полу)формальными методами. Это интересная тема. А то все получается, что система в работу отправляется тогда, когда работать над ней надоело :)
      • Marcello
        17 июня 2015, 14:48
        anatolyutkin, тут похоже другое. К примеру, после пересечения SMA(10) вверх ты ожидаешь, что через определенное число баров (скажем, 4) она не уйдет ниже точки пересечения. Если ты угадываешь в 50% случаев и тебе этого мало, то ищешь другое условие входа, после которого 4-й бар остается в прибыли. По сути, это подгонка под «тейк-профит» (намеренно взял в кавычки).
        • anatolyutkin
          17 июня 2015, 19:02
          Marcello, Ну да, так и есть. Дискретизованное время. Там выше автор дал хорошее определение--см. коммент от 17:21:29.

Активные форумы
Что сейчас обсуждают

Старый дизайн
Старый
дизайн