Количественная торговля: какой день считается «хорошим» для этой акции

Python NumPy pandas IPython

Автор: Абу

Все права принадлежат Abu. Количественная перепечатка запрещена без разрешения.

система количественной оценки abu github address(Добро пожаловать + звезда)

Адрес видеоинструкции по работе с интерфейсом в этом разделе

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

В предыдущем разделе был объяснен пример межрыночного низкочастотного статистического арбитража в количественной торговле. В этом разделе будет проиллюстрирована краткосрочная временная стратегия, связанная с циклом. Содержание этого раздела представляет собой полный пример стратегии для раздела «The Дорога к количественному трейдингу». Пополнение.

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

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

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

  1. Жадность: Жадность играет большую роль в этом. Когда человек покупает акции в первый раз и держит их с определенной прибылью, он решает продать акции, потому что думает, что они подорожали. Их много, пора сделать надлежащую коррекцию, и после этого у цены акций есть только две возможности: первая — упасть в соответствии с его ожиданиями, поэтому он может решить упасть до определенной степени и снова выйти на рынок, чтобы купить акции; во-вторых, продолжать расти, в этом случае он предпочтет постоянно «проклинать» акции, пока однажды цена акций не вырастет настолько, что он не сможет этого выдержать, и от «черного до веера».

  2. Стоимость времени и лень: Человек имеет ограниченное время и энергию, он не может получить информацию обо всех акциях на рынке, и затраты времени на знакомство с акцией также огромны, по его мнению, он постоянно смотрит на себя. которыми чаще всего торгуют.

1. Краткосрочный анализ цикла акций США

Давайте сначала получим годовые данные о запасах Китая и США в данных песочницы в качестве примера краткосрочного анализа:

us_choice_symbols = ['usTSLA', 'usNOAH', 'usSFUN', 'usBIDU', 'usAAPL', 'usGOOG', 'usWUBA', 'usVIPS']
kl_dict = {us_symbol[2:]: 
 ABuSymbolPd.make_kl_df(us_symbol, start='2014-07-26', end='2015-07-26') 
 for us_symbol in us_choice_symbols}

С точки зрения суточного коэффициента изменения амплитуды только BIDU и WUBA едва ли могут иметь место для краткосрочного арбитража (значение > 1,8), но поскольку в данных песочницы есть только эти символы, этот специальный сертификат временно игнорируется, и Данные вне песочницы будут использоваться позже, это значение используется для краткосрочного анализа всего рыночного цикла.

ABuKLUtil.wave_change_rate(kl_dict)
TSLA日振幅涨跌幅比:1.778420
NOAH日振幅涨跌幅比:1.733710
SFUN日振幅涨跌幅比:1.784097
BIDU日振幅涨跌幅比:1.812175
AAPL日振幅涨跌幅比:1.664462
GOOG日振幅涨跌幅比:1.573070
WUBA日振幅涨跌幅比:1.913431
VIPS日振幅涨跌幅比:1.568457

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

  1. Вероятность роста Tesla в четверг составляет 59%.
  2. Богатство Ноя также имеет 65-процентный шанс увеличиться в четверг.
  3. Baidu вырос на 60% в пятницу
  4. Вероятность роста Apple в среду составляет 56%.
ABuKLUtil.date_week_win(kl_dict)

Если временной стратегии необходимо найти каждый торговый день с вероятностью роста акций более 55% в качестве дня для покупки стратегии, например, следующий пример находит торговый день, когда Тесла превышает 55%:

tl_dw = ABuKLUtil.date_week_win(kl_dict['TSLA'])
tl_dw_vd = tl_dw[tl_dw.win > 0.55]
tl_dw_vd

Можно видеть, что приведенный выше результат является торговым днем, требуемым символом, но если коэффициент выигрыша в четверг очень высок, но коэффициент роста в четверг очень низкий, если коэффициент роста очень низок, прибыль-убыток коэффициент будет очень низким, что приведет к окончательной сделке.Все еще теряя деньги, давайте использовать date_week_mean, чтобы увидеть соотношение взлетов и падений в каждый торговый день акций США выше, как показано ниже:

ABuKLUtil.date_week_mean(kl_dict)

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

tl_dwm = ABuKLUtil.date_week_mean(kl_dict['TSLA'])
tl_dwm.loc[tl_dw_vd.index]

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

abs(tl_dwm.sum()).values[0] / 0.618, abs(tl_dwm._p_change).mean() / 0.618
(0.73209375244226405, 0.45709539602153293)

Видно, что значение первого алгоритма рассчитывается как 0,73, второго — 0,45, 0,54 больше 0,45, но меньше 0,73, то есть хотя Тесла имеет высокую вероятность роста в четверг, если первый алгоритм используется, то в конкретной стратегии сигнал на покупку не будет подан, так как процент прибыли не соответствует требованиям.

Примечание:

  1. В приведенном выше расчете 0,618 можно передать через параметры в конкретной стратегии.
  2. Будь то коэффициент выигрыша 55% или 0,618, использованный выше, цель состоит в том, чтобы создать несбалансированное преимущество в вероятности.
  3. При написании фактической стратегии, в соответствии с требованиями к объему торгов, количеством рыночных торговых целей и т. д., определите конкретное использование вышеуказанного алгоритма, или они будут действовать параллельно.

Давайте посмотрим на торговые дни, когда вероятность роста Baidu превышает 55%:

bd_dw = ABuKLUtil.date_week_win(kl_dict['BIDU'])
bd_dw_vd = bd_dw[bd_dw.win > 0.55]
bd_dw_vd

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

bd_dwm = ABuKLUtil.date_week_mean(kl_dict['BIDU'])
print(abs(bd_dwm.sum()).values[0] / 0.618, abs(bd_dwm._p_change).mean() / 0.618)
bd_dwm.loc[bd_dw_vd.index]
0.171504714657 0.2820732168894443

В результате видно, что значение первого алгоритма вычисляется как 0,17, второго — 0,28, а 0,25 больше 0,17, но меньше 0,28, то есть если в стратегии используется первый метод расчета порога , сигнал на покупку будет удовлетворен.

2. Ежедневный винрейт означает стратегию восстановления

Количество символов, используемых на реальном диске, будет намного больше, чем количество данных песочницы, используемых в этом примере.Стратегия может потребовать соблюдения обоих порогов, а для построения окончательного неравновесного результата добавляются дополнительные неравновесные условия. , но из-за этого Например, объем данных в песочнице невелик, поэтому при написании стратегии, приведенной ниже, можно использовать два метода расчета порога для удовлетворения одного из них.Общий принцип стратегии следующий:

Характер стратегии:средняя доходность

  1. По умолчанию период 40 дней (8 недель) используется для расчета дня недели в сочетании с порогом роста и падения, подходит для покупки.
  2. Указанные дни недели пересчитываются один раз в месяц во время тестирования на истории и подходят для покупки.
  3. В задаче дня стратегии сигнал на покупку: вчера упало, открылось сегодня тоже упало, а завтра расчетный "день недели" с высокой вероятностью роста

Конкретная стратегия записывается следующим образом:

Примечание. Пользователи, не знакомые с программированием, могут игнорировать конкретную реализацию кода или могут напрямую использовать пользовательский интерфейс для работы.Адрес видеоурока по работе с пользовательским интерфейсом в этом разделе

class AbuFactorBuyWD(AbuFactorBuyTD, BuyCallMixin):
    def _init_self(self, **kwargs):
        """
            kwargs中可选参数:buy_dw:    代表周期胜率阀值,默认0.55即55%
            kwargs中可选参数:buy_dwm:   代表涨幅比例阀值系数,默认0.618
            kwargs中可选参数:dw_period: 代表分析dw,dwm所使用的交易周期,默认40天周期(8周)
        """
        self.buy_dw    = kwargs.pop('buy_dw', 0.55)
        self.buy_dwm   = kwargs.pop('buy_dwm', 0.618)
        self.dw_period = kwargs.pop('dw_period', 40)

        # combine_kl_pd中包含择时金融时间数据与择时之前一年的金融时间数据, 先取出择时开始之前的周期数据
        last_kl = self.combine_kl_pd.loc[:self.kl_pd.index[0]]
        if last_kl.shape[0] > self.dw_period:
            last_kl = last_kl[-self.dw_period:]
        # 开始计算周几买,_make_buy_date把结果被放在self.buy_date_week序列中
        self._make_buy_date(last_kl)

    def fit_month(self, today):
        """月任务,每一个重新取之前一年的金融时间序列数据,重新计算一遍'周几买'"""
        end_ind = self.combine_kl_pd[self.combine_kl_pd.date == today.date].key.values[0]
        start_ind = end_ind - self.dw_period  if end_ind - self.dw_period  > 0 else 0
        # 根据当前的交易日,切片过去的一年金融时间序列
        last_kl = self.combine_kl_pd.iloc[start_ind:end_ind]
        # 重新计算一遍'周几买'
        self._make_buy_date(last_kl)

    def fit_day(self, today):
        """日任务:昨天下跌,今天开盘也下跌,根据今天是周几,在不在序列self.buy_date_week中决定今天买不买"""
        if self.yesterday.p_change < 0 and today.open < self.yesterday.close \
            and int(today.date_week) in self.buy_date_week:
            # 由于没有用到今天的收盘价格等,可以直接使用buy_today
            return self.buy_today()
        return None

    # noinspection PyProtectedMember
    def _make_buy_date(self, last_kl):
        self.buy_date_week = []
        # 计算周期内,周期的胜率
        last_dw = ABuKLUtil.date_week_win(last_kl)
        # 摘取大于阀值self.buy_dw的'周几',buy_dw默认0.55
        last_dw_vd = last_dw[last_dw.win >= self.buy_dw]
        """
            eg: last_dw_vd
                       0  1   win
            date_week            
            周四         3  5  0.62
            周五         2  6  0.75
        """
        if len(last_dw_vd) > 0:
            # 如果胜率有符合要求的,使用周几平均涨幅计算date_week_mean
            last_dwm = ABuKLUtil.date_week_mean(last_kl)
            # 摘取满足胜率的last_dw_vd
            last_dwm_vd = last_dwm.loc[last_dw_vd.index]
            """
                eg: last_dwm_vd
                           _p_change
                date_week           
                周四              1.55
                周五              1.12
            """
            # 阀值计算方式1
            dwm1 = abs(last_dwm.sum()).values[0] / self.buy_dwm
            # 阀值计算方式2
            dwm2 = abs(last_dwm._p_change).mean() / self.buy_dwm
            # 如果symbol多可以使用&的关系
            dm_effect = (last_dwm_vd._p_change > dwm1) | (last_dwm_vd._p_change > dwm2)
            buy_date_loc = last_dwm_vd[dm_effect].index
            """
                eg: buy_date_loc
                Index(['周四', '周五'], dtype='object', name='date_week')
            """
            if len(buy_date_loc) > 0:
                # 如果涨跌幅阀值也满足,tolist,eg:['周一', '周二', '周三', '周四', '周五']
                dw_index = last_dw.index.tolist()
                # 如果是一周5个交易日的就是4,如果是比特币等7天交易日的就是6
                max_ind = len(dw_index) - 1
                for bdl in buy_date_loc:
                    sell_ind = dw_index.index(bdl)
                    buy_ind = sell_ind - 1 if sell_ind > 0 else max_ind
                    self.buy_date_week.append(buy_ind)

3. Средняя стратегия восстановления ежедневного коэффициента выигрыша каждого рыночного тестирования на исторических данных.

Вышеупомянутый AbuFactorBuyWD завершил написание всей стратегии, и начинается тестирование на исторических данных, как показано ниже:

# 初始化资金
read_cash = 1000000
# 买入策略AbuFactorBuyWD,参数都使用默认的
buy_factors = [{'class': AbuFactorBuyWD}]
# 卖出策略使用AbuFactorSellNDay,sell_n=1即只持有一天,is_sell_today=True, 持有一天后当天卖出
sell_factors = [{'class': AbuFactorSellNDay, 'sell_n': 1, 'is_sell_today': True}]

# 开始进行美股沙盒数据回测,沙盒数据中美股只有从13年7月到16年7月的数据,其它市场会多一些
abu_result_tuple = run_loo_back(us_choice_symbols, '2013-07-26', '2016-07-26')
买入后卖出的交易数量:146
买入后尚未卖出的交易数量:2
胜率:53.4247%
平均获利期望:1.9614%
平均亏损期望:-1.9299%
盈亏比:1.1534
所有交易收益比例和:0.2369 
所有交易总盈亏和:24655.9100 

Видно, что процент выигрышей в вышеупомянутом бэктесте превышает 50% Из приведенного ниже списка транзакций мы видим, что все транзакции удерживаются только в течение одного дня, а именно:

abu_result_tuple.orders_pd.filter(
    ['symbol', 'buy_date', 'sell_date', 'keep_days', 'profit'])[:7]

В приведенной выше стратегии торговый период с наибольшей вероятностью повышения «дня недели» по умолчанию составляет 40 дней (8 недель).Продолжительность этого периода не может быть слишком длинной или слишком короткой, потому что активные пользователи на определенные акции существуют только в течение короткого периода времени Не так много изменилось, но игроки на рынке медленно меняются с течением времени, постоянно меняя старые и новые, точно так же, как мы, люди, мы являемся совершенно новым я каждые 7 лет, и все клетки и кровь снова полностью обновятся.

Давайте воспользуемся этой стратегией для тестирования биткойнов и лайткойнов следующим образом:

_ = run_loo_back(['btc', 'ltc'], '2013-07-26', '2017-07-26')
买入后卖出的交易数量:24
买入后尚未卖出的交易数量:0
胜率:58.3333%
平均获利期望:2.8335%
平均亏损期望:-2.6652%
盈亏比:1.8846
所有交易收益比例和:0.1302 
所有交易总盈亏和:18321.1800 

Следующее использует рыночный символ A-акции в этой песочнице для тестирования на исторических данных, как показано ниже:

cn_choice_symbols = ['002230', '300104', '300059', '601766', '600085', '600036', '600809', '000002', '002594']
_ = run_loo_back(cn_choice_symbols, '2013-07-26', '2017-07-26')
买入后卖出的交易数量:112
买入后尚未卖出的交易数量:1
胜率:55.3571%
平均获利期望:1.8545%
平均亏损期望:-2.0521%
盈亏比:1.0527
所有交易收益比例和:0.1237 
所有交易总盈亏和:6612.0000 

резюме:

Вышеупомянутая транзакция на исторических данных использует данные песочницы и имеет небольшой объем данных, поэтому фактический эффект на исторических данных является средним, то есть, если стратегия имеет коэффициент выигрыша 56%, то в день выполняется только 10 транзакций, а ваш коэффициент выигрыша различные возможности.Не обязательно 56%, но если вы можете выполнять более 10 000 раз в день, то если ваш винрейт не 56%, больше или меньше, то это означает, что есть проблема с тем, как вы рассчитываете шанс на победу.

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

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

Другие технические статьи по квантованию Абу

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