3Qu
3Qu личный блог
19 июня 2020, 16:32

Python. Делаем тестер стратегий и... зарабатываем на случайном блуждании.

Если вам кто нибудь скажет, что на случайном блуждании (СБ) нельзя зарабатывать, бросьте в него камень. Как говорил Паниковский — это жалкие ничтожные люди. На СБ можно зарабатывать с результатами не хуже, чем на реальном рынке. У СБ, по сравнению с реальным рынком, только один недостаток — за игры с СБ никто деньги платить не будет.
А если бы платили? Никто бы ничего не заметил. По прежнему 95% СБ-трейдеров сливало бы депозиты, а 5% регулярно выигрывало и считало бы себя Гуру. По прежнему на графики наносились бы каббалистические знаки и индикаторы, угадывались бы направления движения, каналы, и линии поддержки/сопротивления. Все так же начинающие трейдеры искали Учителя для обучения, а аналитики предсказывали будущее. И, ровным счетом, абсолютно ничего бы не поменялось. Может только АГ заметил бы подвох, но тоже не сразу, а только через несколько месяцев, а, может, и через год-другой. Но, легко сделать, чтобы и АГ остался в неведении.)

Однако, прежде чем играть на СБ, нам необходима стратегия и тестер. Ими мы и займемся.
Для начала стратегия: нам нужны три функции
— одна для пошагового слежения за рыночными котировками и определения момента входа в сделку — DealEntryAnalysis(i) и пусть на ее выходе будет: 0-если сделки нет, 1 — необходим вход в лонг, и -1 — необходим вход в шорт. i — номер отсчета массива котировок.
— вторая для сопровождения сделки лонг — DealControlL(i), отвечающая за контроль и закрытие сделки.
— и третья, для сопровождения сделки шорт — DealControlS(i).
Теперь у нас все готово для разработки тестера стратегий, а это всего лишь цикл while() последовательно перебирающий котировки.
Вот наша стратегия уже в тестере:

while i < Ie:
    deal_type = DealEntryAnalysis(i)
    if deal_type == 1:
        j, rep = DealControlL(i)
        deals_report.append(rep)
        i = j+1
        continue
    elif deal_type == -1:
        j, rep = DealControlS(i)
        deals_report.append(rep)
        i = j+1
        continue
    i = i+1

deals_report — это отчет о проделанной работе по каждой из сделок, а j — номер отсчета выхода из сделки.

Ну, а какую стратегию выбрать для работы с СБ — лучше всего тоже случайную: случайный вход в сделку, и случайный выход из нее.
Выбор когда входить и в какую сделку — шорт или лонг сделаем так:

def DealEntryAnalysis(i):
    rnd1 = np.random.default_rng().uniform(0, 1)
    if rnd1 < 0.99:
        return 0
    else:
        rnd1 = np.random.default_rng().uniform(0, 1)
    if rnd1 > 0.5:
        return 1
    else:
        return -1

Здесь мы выбрали, что вероятность входа в сделку всего 0.01, а лонг или шорт выбираем с вероятностью 0.5.
Функция сопровождения сделки делается примерно аналогично — полный код всей стратегии и тестера см. в конце топика.

Запускаем наш тестер, и получаем:
Python. Делаем тестер стратегий и... зарабатываем на случайном блуждании.Python. Делаем тестер стратегий и... зарабатываем на случайном блуждании.

Вот сами видите, можно же зарабатывать. Мы уже Гуру трейдинга на СБ, можем набирать учеников. Конечно, многие скажут — 500 сделок, интервал маловат, надо минимум 1000. — Не проблема, сейчас покажем и 1000 сделок.
Обольщаться не надо, такие результаты доступны только ~10% трейдеров, но многие могут прибыльно торговать на СБ тоже с неплохими результатами. Вот с 1000 сделками дела похуже — Гуру становится меньше и успешные трейдеры потихоньку рассасываются. Но, при всем при том, истинные профессионалы, их немного, но даже на таком случайном рынке все равно остаются. В общем, на СБ вполне можно рассчитывать на ~5% успешных трейдеров, ну, а истинные гуру — их всегда мало, где-то доли процента. И в завершение, код нашей стратегии.
Что мы в итоге получили? А получили, что игры на СБ, по крайней мере по показателям успешности трейдеров, статистически не отличаются от игр на реальных биржевых инструментах.

import numpy as np
import matplotlib.pyplot as plt
# import SLPack.Filters as flt  # загрузка нашего пакета

mu = 0  # матожидание
sigma = 5  # стандартное отклонение
N = 50000  # длина последовательности

# нормально распределенная случ последовательность
normrand = np.random.default_rng().normal(mu, sigma, N)

rw = []
# создаем случ блуждание
for i in range(0, N):
    if i == 0:
        rw.append(10000+normrand[i])
    else:
        rw.append(rw[i-1] + normrand[i])

# F8 = flt.cF1Bat(8, rw)
# F16 = flt.cF1Bat(16, rw)
# FM16 = flt.cFMean(16, rw)


# анализ входа в сделку
def DealEntryAnalysis(i):
    rnd1 = np.random.default_rng().uniform(0, 1)
    if rnd1 < 0.99:
        return 0
    else:
        rnd1 = np.random.default_rng().uniform(0, 1)
    if rnd1 > 0.5:
        return 1
    else:
        return -1


# сопровождение сделки Long
def DealControlL(i):
    rep = [1, i, 0, rw[i], 0, 0]  # отчет о сделке Long
    ie = i+5
    rep[2] = ie
    rep[4] = rw[ie]
    rep[5] = rw[ie]-rw[i]
    return ie, rep


# сопровождение сделки Short
def DealControlS(i):
    rep = [-1, i, 0, rw[i], 0, 0]  # отчет о сделке Short
    ie = i+5
    rep[2] = ie
    rep[4] = rw[ie]
    rep[5] = rw[i]-rw[ie]
    return ie, rep


Ib = 20
Ie = 50000-10
i = Ib
deals_report = []

while i < Ie:
    deal_type = DealEntryAnalysis(i)
    if deal_type == 1:
        j, rep = DealControlL(i)
        deals_report.append(rep)
        i = j+1
        continue
    elif deal_type == -1:
        j, rep = DealControlS(i)
        deals_report.append(rep)
        i = j+1
        continue
    i = i+1

profit = []
for i in range(0, len(deals_report)):
    if i == 0:
        profit.append(deals_report[i][5])
    else:
        profit.append(profit[i-1]+deals_report[i][5])

plt.plot(profit)
plt.title('Profit')
plt.legend()
plt.grid()
plt.show()

На этом, думаю, можно завершить цикл топиков о моделировании торговых систем на Python. [1],[2] Все необходимые инструменты для тестирования ваших стратегий в Python готовы к применению.

Ссылки.

1. Моделирование Торговых Систем на Python. 1.

2. Моделирование Торговых Систем на Python. 2.

20 Комментариев
  • ака Tуземец
    19 июня 2020, 17:33
    это одним контрактом, безо всяких условий и без Горчаковских умных «приращений».по- нашему, по-бразильски
  • Susanin
    19 июня 2020, 17:57
    А если добавить следящий стоп, а не выход по случайности. Результаты по идее должны быть не много лучше.
  • зщшгнекуцй
    19 июня 2020, 19:09
    Как вы думаете, почему при случайном входе и TP/SL=2/1 результат стремится к 0 — комиссия ? 
  • Свой Мужик
    20 июня 2020, 12:32
    А прогони плз у себя тест если вместо
    if rnd1 > 0.5:
    поставить

    if rnd1 > 0.6:

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

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