Нефть глазами аналитика данных

от автора

Любите ли вы работать с данными, как люблю это делать я? Страдаете ли вы также от несовершенства инструментов для анализа данных? И вот, буквально в первых строках, я понимаю, что мне надо быть очень аккуратным, дабы не задеть чувства, к примеру, фанатов Excel или Notepad++. Попытаюсь исправить ситуацию: Эксель великолепен! Лучшая low-code система! Notepad++ бесподобен… но попробуйте поработать этими инструментами с данными размером с один миллион строк… эх, не удержался. Ну и раз статья обещает быть провокационной, добавлю еще огоньку: я хочу продемонстрировать, как обрабатывать и анализировать данные по всем обезличенным сделкам по нефти. Взглядом аналитика покажу, как крупный капитал управляет рынком. И да, я хочу, чтобы такая возможность была доступна не только корпорациям с их ресурсами, а обычному пользователю с ноутбуком. Текст статьи не является инвестиционной рекомендацией, все совпадения случайны.

Краткое вступление

Написание статьи как и сбор данных осуществлялись в первой половине января 2024 года. Поэтому предметом анализа выступали обезличенные сделки по расчетному фьючерсу на нефть (BRG4) в период начиная с начала вечерней сессии 12.01.2024 заканчивая финалом дневной сессии от 17.01.2024.

Содержание

  1. Способ получения и подготовки данных
  2. Хранение и загрузка данных
  3. Анализ данных

Способ получения данных

Опишу, как сделать это бесплатно, но у вас должен быть активный торговый терминал Quik. Да, есть сервис московской биржи, который очень скупо делится данными. Да, мне понравилась задумка tinkoff отдавать все через API-шечку (обожаю Swagger). Но повторюсь, для обычного пользователя это сложновато. Открываем терминал Quik, желательно ближе к концу дневной сессии (18-45 МСК). Время выбрано не случайно, т.к. через терминал у вас есть возможность получить данные всего за один день (если быть точнее за вечернюю сессию предыдущего дня и за дневную сессию текущего).

Выбираем меню -> Создать окно -> Таблица обезличенных сделок

В открывшемся окне выставляем параметры как показано на рисунке:

В открывшейся таблице обезличенных сделок щелкаем правой кнопкой мыши и выбираем «Копировать все» как показано на рисунке:

Далее, начинается первое испытание силы вашей любви к Notepad++ 🙂 Вставьте содержимое буфера обмена в Notepad++. Скажу честно, я не справился, слукавил и воспользовался VSCode. Тем не менее, после вставки в текстовый файл данные выглядят примерно вот так:

Далее в текстовом файле необходимо выполнить серию замен, чтобы немного снизить размер файла и подготовить полноценный csv файл. Я обычно подменяю:

  • Все запятые на точки
  • Все табы на запятые
  • слово «Купля» на символ ‘B’
  • слово «Продажа» на символ ‘S’
  • ну и т.д.

Должно все получится вот примерно в таком виде:

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

Хранение и загрузка данных

На самом деле, здесь уже вопрос предпочтений и удобства. Данные можно хранить в виде csv файлов. Мой путь — более сложный, но все же опишу его. Я лично предпочитаю использовать СУБД, любимый Clickhouse от yandex. При таком подходе у получаю гибкость, например, я могу дать такой SQL-запрос:

 SELECT ID_DTTM, OPERATION, PRICE, QUANTITY, OI FROM moex.br_trades bt where bt.ID_DTTM>toDateTime('2024-01-16 08:50:00') and bt.ID_DTTM<toDateTime('2024-01-17 00:00:00') order by bt.ID_DTTM

… и получу сразу набор данных в период с 08:50 16.01.24 по 00:00 17.01.24 отсортированный по дате и времени. В случае с хранением данных в формате csv — о такой гибкости можно и не мечтать.

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

Как загрузить данные из csv в clickhouse. Я использую DBeaver и простенький Python-скрипт, например, вот такой:

Простой скрипт

INSERT_SQL = "INSERT INTO moex.br_trades (ID_DTTM, TRADENO, SECID, PRICE, QUANTITY, OPERATION, OI) VALUES " with open("./br_in_16-17.csv") as file: content = file.readlines()  sql = INSERT_SQL for line in content: trade = line.split(",") tradeno = trade[1] id_dttm = trade[2] + " " + trade[3] secid = trade[4] price = trade[5] quantity = trade[6] operation = trade[7] oi = trade[8]  sql = ( INSERT_SQL + "(toDateTime('" + id_dttm + "'),'" + tradeno + "','" + secid + "'," + price + "," + quantity + ",'" + operation + "'," + oi + ");" )  print(sql) 

Примерно в этом месте должны появится «душнилы», которые скажут, что в аналитические СУБД данные надо грузить батчами (batch), а не построчно. На практике же DBeaver умирает примерно перед запуском батча размером от 100 тыс. строк и выше. А построчно медленно, но выполняет.

Анализ данных

Здесь также тропинка к результату проходила через болото разочарования. Я было ринулся рисовать графики в Apache Superset, но тот сразу «покинул чат», замерев навечно при отрисовке скромного датасета размером в 300 тыс. строк. Да, понимаю, дело всего в одном воркере и скверной манере данной BI-системы оборачивать исходный SQL-датасета в свой. Как итог – здравствуй, Jupyter Notebook.

Установку рекомендую через Anaconda

Первым делом импортируем нужные пакеты, и в датафрейм df загрузим данные (или из csv файла, или из clickhouse), ну и посмотрим что у нас получилось.

Здесь, для понимания, опишу значения в колонках

  • ID_DTTM – дата и время сделки
  • OPERATION – “B”: покупка, “S”: продажа
  • PRICE – цена сделки
  • QUANTITY – количество (лотов)
  • OI – открытый интерес

Немного статистики:

Обратите внимание на минимальные и максимальные значения столбца Quantity, нам это потребуется в дальнейшем.

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

Отлично, но пока скромно. Любой торговый терминал так может. А теперь давайте нарисуем то, чего не могут терминалы (или не хотят). Например, меня очень давно интересовала корреляция между покупками/продажами и открытым интересом. Пусть у нас будет новый столбец в датафрейме, назовем его дельтой. Суть дельты – накапливаемая с начала выборки разница между покупкой и продажей. Например, если у нас с начала периода продали 18 лотов, потом купили 1, а потом снова продали 5, то дельта = -18 + 5 – 1 = — 14 лота.

А теперь посмотрим на примере графика:

А вот уже интересные выводы:

  1. Несмотря на то, что за 16 января цена нефти почти не изменилась (если сравнивать начало дня и конец дня) – тем не менее все участники рынка по итогам дня выкупили около 7500 лотов. Интересно, почему так случилось, правда?
  2. С открытым интересом — можно, конечно, и точно посчитать, но явно видна обратная корреляция между дельтой и интересом. Т.е. когда рынок покупает, открытый интерес падает ну и наоборот.

Теперь давайте разделим нашу дельту на составные части. Ведь в нашей выборке обезличенных сделок присутствуют сделки от всех участников рынка, независимо от размера. Вот мы их и разделим по размеру сделки. Помните, я просил вас запомнить минимальное и максимальное значение количества лотов в сделке? Оно в данном случае от 1 лота до 500. Давайте возьмем сделки размером более 100 лотов и посчитаем по ним дельту отдельно. Является ли данный признак подходящим для определения крупной сделки? Думаю, что да. Покупатель/продавец под 1 лот фьючерса BRG4 должен иметь обеспечение на сумму около 14 тыс. руб. Следовательно под 100 лотов речь идет уже о обеспечении в 1.4 млн руб. Еще раз, 1.4 млн руб. – это только обеспечение по всего одной сделке. Так что думаю вполне.

Вот что получилось.

Оранжевая кривая – мелкие сделки, красная – крупные. И тут мы с вами оказываемся на тонком льду интерпретации результатов. Воображаемые «сторонники заговора маркетмейкеров против спекулянтов» могут сказать «ну все очевидно, когда цена начала падать, поддержали рынок, а дальше гнали толпу наверх». Ну, а если опираться на цифры, то мы видим, что посредством крупных сделок к концу дня выкуплено около 2500 лотов, а вот посредством мелких – 5000 лотов.

Но лично мне хотелось бы получить четкий признак локальных экстремумов. Если говорить упрощенно, я хотел бы в ситуации, когда цена упала – понимать, что «это дно и дальше будем расти», или в ситуации, когда цена растет – понимать, «это вершина, скоро начнем падать». И, буду честен, мне пока не удалось этого достичь. Но, ведь и цель статьи была в другом, верно?

Послесловие

Ссылка на git c csv файлами выгрузки и файлом jupyter notebook

В статье я старался продемонстрировать возможность для обычного пользователя заниматься анализом большого объема данных. Да, таким же способом можно анализировать не только инструменты срочного рынка, а, к примеру, сделки по акциям. Можно ли построить успешную стратегию на основе данного анализа? Уверен, что да. И даже протестировать. Но, думаю это материал уже для следующей статьи и следующей бессонной ночи.


ссылка на оригинал статьи https://habr.com/ru/articles/788668/


Комментарии

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *