Постов с тегом "программирование": 332

программирование


Быстрый бектестинг стратегии на python с pandas

Я уже давно использую для бектестов python и pandas. pandas это библиотека для работы с матрицами и её прелесть в том, что она оперирует векторами и работает ГОРАЗДО быстрее, чем обычные циклы. Для того, чтобы сохранить это достоинство при бектестах я использую логарифмическую доходность (log-return на английском). Не ручаюсь за русские термины, так как узнал про них из англоязычных статей. Написанное ниже не истина в первой инстанции, а моя попытка разобраться как это всё работает чтобы применять на практике. Если я не прав, напишите. Я хоть и защищал кандидатскую диссертацию, но не по математике или экономике.

Немного теории



Логарифмическая доходность — разница стоимости актива в разные промежутки времени в процентах. Рассчитываеся по такой формуле:  
Быстрый бектестинг стратегии на python с pandas


Формула для расчёта логарифмической доходности, логарифм натуральный

Теперь на примере акций теслы. Цена по дням:  

( Читать дальше )

Использование API Fmp Cloud для отбора акций по дивидендам на Nasdaq с помощью Python

    • 21 марта 2021, 20:02
    • |
    • Aleks
  • Еще

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

Что такое дивидендная доходность?

Возьму определение из Википедии. Дивиде́ндная дохо́дность (англ. dividend yield) — это отношение величины годового дивиденда на акцию к цене акции. Данная величина выражается чаще всего в процентах.

Пример

При цене акции ОАО «Лукойл» 1124,37 рублей и дивиденде 28 рублей на акцию дивидендная доходность будет равна:

Использование API Fmp Cloud для отбора акций по дивидендам на Nasdaq с помощью Python
Так же необходимо обратить внимание, что многие растущие компании, такие как для примера Amazon и Yandex, не выплачивают дивиденды, поскольку они реинвестируют всю прибыль в развитие бизнеса. Поэтому дивидендная доходность для этих фирм будет равна нулю.

Расчет дивидендной доходности с помощью Python



( Читать дальше )

Завершающий этап оценки привлекательности покупки акций! От возможных цен к доходностям!

Этот пост — последняя часть из цикла постов посвященных механистической оценке привлекательности инвестиций на основе фундаментальных показателей.

[1] Начало здесь: "Фундаментальный анализ тоже поддается автоматизации и вероятностному прогнозированию"
[2] Продолжение: "От прогноза фин показателей компании к прогнозам возможных цен на бирже"

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

Но давайте вкратце вспомним, основные промежуточные результаты, которые я получил в первых двух постах. Здесь немного уточню, чтобы расчеты были более корректны. Сама отчетность за 2014 год была составлена 23 марта 2015. Я, конечно, уже не помню, когда она была опубликована, поэтому буду считать что я смог ее посмотреть 31 марта 2015 и провести все те расчеты, которые я демонстрировал в предыдущих постах.



( Читать дальше )

От прогноза фин показателей компании к прогнозам возможных цен на бирже

Продолжение статьи "Фундаментальный анализ тоже поддается автоматизации и вероятностному прогнозированию" и не только...

Теперь поговорим немного о мультипликаторах и их использовании в прогнозировании. Нужно понимать, что когда от статей отчетности мы переходим к ценовым мультипликаторам, мы ступаем на очень зыбкую почву. Частично о ловушках того же популярного мультипликатора P/E я уже писал в своем посте: "Дорого или дешево стоят акции на Московской Бирже? И ловушка показателя P/E!", поэтому трактовать моделирование нужно с осторожностью и немалой долей здравого смысла.

Вернусь к примеру по акциям ПАО МАГНИТ.
P/E Магнит до 2015 года
Мастодонты фондового рынка, такие как Грэм, хорошо понимая недостатки этого показателя советовали при его расчете и принятии решения использовать для среднюю прибыль за 5, 7 или 10 лет, позже Роберт Шиллер выбрал в качестве знаменателя 10-летнюю среднюю прибыль с поправкой на инфляцию. Если огрубить идею инвестиций на основании коэффициента P/E, то можно было бы вывести следующее простое правило:



( Читать дальше )

Обучение для новичка

Добрый день! 
Это мой первый пост на смарт-лабе, частенько его читал, но никогда ничего не писал. 
Торгую не так давно около года, руками. До этого был инвестором, вкладывался в бумаги Газпрома, Сбербанка, Мосбиржи, Северстали… Покупал разные бумаги, акции росли, я их продавал, иногда не сильно везло… акции падали — тогда просто сидел, ждал пока отрастут. 
Но тут всегда лотерея — никогда не знаешь, что будет в прибыли или убытке. Сейчас хочу попробовать свои силы в системной торговле. Поставил ТСлаб, осваиваю кубики. Опыта программирования считайте не ту, языков программирования не знаю. Знаю английский. 
Хочу пойти на курсы по алготрейдингу, почитал отзывы в интернете, да и тут на смарт-лабе, курсов много… разные… и отзывы разные ... 
Ищу что-то такое, чтобы потом не жалко было потраченных денег и времени. Посоветуйте что-то хорошее, проверенное, чтобы учили работающим, понятным методам. Не подгонкам и чтобы не просто вода: чтобы методы можно было протестировать. 
п.с. Также интересует как лучше всего прокачать программирование — склоняюсь к c#, TSlab на с# написан. 
Заранее Спасибо за любые советы!!! 
Всем успехов в торгах!

Кодирование свечей по Лиховидову

Кодирование свечей по Лиховидову.
Параметры большой, средний, маленький берутся по свечам того же времени предшествующих дней.
Может кому пригодится для ML.
А может ошибки найдете или улучшение предложите.

# -*- coding: utf-8 -*-
"""
Читает файл csv в DataFrame. Добавляет колонку с кодом свечи по Лиховидову.
Расчет (большой, средний, маленький) ведется по свечам тогоже времени за предшествующие дни.
Количество предшествующих дней выбирается. Нужно предусмотреть csv файл с большей историей чем start_date на day_delta
"""
import pandas as pd
import numpy as np
from pathlib import Path


class CandleCode:
    def __init__(self, start_date, day_delta, dir_source, file_source):
        self.start_date = start_date
        self.day_delta = day_delta
        self.df = pd.DataFrame()
        self.dir_source = dir_source
        self.file_source = file_source

    def csv_to_df(self):
        """
        Читает файл csv delimiter=';' в DataFrame
        :param dir_source: Папка откуда берем csv файл для обработки
        :param file_source: Исходный файл
        :return:
        """
        self.df = pd.read_csv(f'{self.dir_source}/{self.file_source}', delimiter=';')  # Загружаем файл в DF
        # Меняем индекс и делаем его типом datetime
        self.df = self.df.set_index(pd.to_datetime(self.df['date_time'], format='%Y-%m-%d %H:%M:%S'))
        # Удаляем колонку с датой и временем, т.к. дата и время у нас теперь в индексе
        self.df = self.df.drop('date_time', axis=1)

    def prev_df_to_dic_code(self, previous_df):
        """
        Из DataFrame предшествующего расчетной свече создает словарь с перцентилями для расчета
        (большой, средний, маленький) диапазон тела свечи и его теней.
        :param previous_df: Получает  аргументе DataFrame, с такимже временем свечей, предшествующий расчетной свече
        :return: Возвращяет словарь перцентилей 33% и 66%
        """
        percentile_dic = {}  # Создаем пустой словарь в который будем писать перцентили
        for index, row in previous_df.iterrows():  # Перебираем строки dataframe previous_df
            if row['open'] > row['close']:  # Свеча на понижение
                previous_df.loc[index, 'shadow_high'] = row['high'] - row['open']
                previous_df.loc[index, 'shadow_low'] = row['close'] - row['low']
                previous_df.loc[index, 'candle_body'] = row['open'] - row['close']
            else:  # Свеча на повышение
                previous_df.loc[index, 'shadow_high'] = row['high'] - row['close']
                previous_df.loc[index, 'shadow_low'] = row['open'] - row['low']
                previous_df.loc[index, 'candle_body'] = row['close'] - row['open']

        percentile_dic['shadow_high_33'] = np.percentile(previous_df['shadow_high'], 33)
        percentile_dic['shadow_high_66'] = np.percentile(previous_df['shadow_high'], 66)
        percentile_dic['shadow_low_33'] = np.percentile(previous_df['shadow_low'], 33)
        percentile_dic['shadow_low_66'] = np.percentile(previous_df['shadow_low'], 66)
        percentile_dic['candle_body_33'] = np.percentile(previous_df['candle_body'], 33)
        percentile_dic['candle_body_66'] = np.percentile(previous_df['candle_body'], 66)
        return percentile_dic

    def file_out(self, start, end, df_candle_code):
        """
        Функция записывает результирующий DF в csv файл
        :param start: Для имени выходного файла, начальная дата
        :param end: Для имени выходного файла, конечная дата
        :param df_candle_code: DataFrame который записываем в файл
        :return:
        """
        name_file_out = Path(f'{self.dir_source}/{self.file_source[:-4]}_{start}_{end}_lihovidov.csv')
        df_candle_code.to_csv(name_file_out)

    def run(self):
        df_candle_code = self.df.copy()  # Создаем копию DF, исключение предупреждений
        # Срез DF в котором будет дополнительная колонка с кодами свечей
        df_candle_code = df_candle_code.loc[self.start_date:]
        df_candle_code['candle_code'] = np.nan  # Создание дополнительного столбца и заполнение его NaN
        for index, row in df_candle_code.iterrows():  # Перебираем строки dataframe df_candle_code
            print()
            print(index)
            delta_day = pd.to_timedelta(f'{self.day_delta} days')  # Преобразование типа
            start_previous_df = index.date() - delta_day  # Вычисляем начальную дату DF
            end_previous_df = index.date() - pd.to_timedelta('1 days')  # Вычисляем конечную дату DF
            # Создаем DF предшествующий текущей строке
            previous_df = self.df.loc[start_previous_df.strftime("%Y-%m-%d"): end_previous_df.strftime("%Y-%m-%d")]
            previous_df = previous_df.loc[index.time()]  # Оставляем только строки соответствующие времени тек. строки

            percentile_dic = self.prev_df_to_dic_code(previous_df)  # Получаем словарь перцентилей

            code_str = ''  # Строка в которую будем собирать код для текущей свечи
            # Свеча на понижение (медвежья)
            if row['open'] > row['close']:  # Свеча на понижение (медвежья)
                code_str += '0'
                # Для тела медвежьей свечи
                if row['open'] - row['close'] > percentile_dic[
                    'candle_body_66']:  # 00 - медвежья свеча с телом больших размеров
                    code_str += '00'
                elif row['open'] - row['close'] > percentile_dic[
                    'candle_body_33']:  # 01 - медвежья свеча с телом средних размеров
                    code_str += '01'
                elif row['open'] - row['close'] > 0:  # 10 - медвежья свеча с телом небольших размеров
                    code_str += '10'
                # Для верхней тени медвежьей свечи
                if row['high'] - row['open'] > percentile_dic['shadow_high_66']:  # 11 - верхняя тень больших размеров
                    code_str += '11'
                elif row['high'] - row['open'] > percentile_dic['shadow_high_33']:  # 10 - верхняя тень средних размеров
                    code_str += '10'
                elif row['high'] - row['open'] > 0:  # 01 - верхняя тень небольших размеров
                    code_str += '01'
                else:  # 00 - верхняя тень отсутствует
                    code_str += '00'
                # Для нижней тени медвежьей свечи
                if row['close'] - row['low'] > percentile_dic['shadow_low_66']:  # 00 - нижняя тень больших размеров
                    code_str += '00'
                elif row['close'] - row['low'] > percentile_dic['shadow_low_33']:  # 01 - нижняя тень средних размеров
                    code_str += '01'
                elif row['close'] - row['low'] > 0:  # 10 - нижняя тень небольших размеров
                    code_str += '10'
                else:  # 11 - нижняя тень отсутствует
                    code_str += '11'

            # Свеча на повышение (бычья)
            elif row['open'] < row['close']:  # Свеча на повышение (бычья)
                code_str += '1'
                # Для тела бычьей свечи
                if row['close'] - row['open'] > percentile_dic[
                    'candle_body_66']:  # 11 - бычья свеча с телом больших размеров.
                    code_str += '11'
                elif row['close'] - row['open'] > percentile_dic[
                    'candle_body_33']:  # 10 - бычья свеча с телом средних размеров
                    code_str += '10'
                elif row['close'] - row['open'] > 0:  # 01 - бычья свеча с телом небольших размеров
                    code_str += '01'
                # Для верхней тени бычьей свечи
                if row['high'] - row['close'] > percentile_dic['shadow_high_66']:  # 11 - верхняя тень больших размеров
                    code_str += '11'
                elif row['high'] - row['close'] > percentile_dic[
                    'shadow_high_33']:  # 10 - верхняя тень средних размеров
                    code_str += '10'
                elif row['high'] - row['close'] > 0:  # 01 - верхняя тень небольших размеров
                    code_str += '01'
                else:  # 00 - верхняя тень отсутствует
                    code_str += '00'
                # Для нижней тени бычьей свечи
                if row['open'] - row['low'] > percentile_dic['shadow_low_66']:  # 00 - нижняя тень больших размеров
                    code_str += '00'
                elif row['open'] - row['low'] > percentile_dic['shadow_low_33']:  # 01 - нижняя тень средних размеров
                    code_str += '01'
                elif row['open'] - row['low'] > 0:  # 10 - нижняя тень небольших размеров
                    code_str += '10'
                else:  # 11 - нижняя тень отсутствует
                    code_str += '11'

            # Дожи
            else:  # Дожи
                if row['high'] - row['open'] > row['open'] - row['low']:  # Верхняя тень больше, медвежий дожи
                    code_str += '011'
                else:  # Верхняя тень меньше, бычий дожи
                    code_str += '100'
                    # Для верхней тени дожи
                if row['high'] - row['close'] > percentile_dic['shadow_high_66']:  # 11 - верхняя тень больших размеров
                    code_str += '11'
                elif row['high'] - row['close'] > percentile_dic[
                    'shadow_high_33']:  # 10 - верхняя тень средних размеров
                    code_str += '10'
                elif row['high'] - row['close'] > 0:  # 01 - верхняя тень небольших размеров
                    code_str += '01'
                else:  # 00 - верхняя тень отсутствует
                    code_str += '00'
                # Для нижней тени дожи
                if row['open'] - row['low'] > percentile_dic['shadow_low_66']:  # 00 - нижняя тень больших размеров
                    code_str += '00'
                elif row['open'] - row['low'] > percentile_dic['shadow_low_33']:  # 01 - нижняя тень средних размеров
                    code_str += '01'
                elif row['open'] - row['low'] > 0:  # 10 - нижняя тень небольших размеров
                    code_str += '10'
                else:  # 11 - нижняя тень отсутствует
                    code_str += '11'

            df_candle_code.loc[[index], ['candle_code']] = int(code_str, 2)
            print(int(code_str, 2))

        self.file_out(df_candle_code.index[0].date(), df_candle_code.index[-1].date(), df_candle_code)


if __name__ == '__main__':
    dir_source = 'c:/data_prepare_quote_csv'  # Папка откуда берем csv файл для обработки
    file_source = 'SPFB.RTS_5min.csv'  # Исходный файл
    start_date = '2020-09-01'  # С какой даты будем строить DF с кодами свечей
    day_delta = 365  # Дельта в днях для расчета показателей (большой, средний, маленький). Предшествует start_date

    code = CandleCode(start_date, day_delta, dir_source, file_source)
    code.csv_to_df()
    code.run()

Очередной раз или учим программированию

Сегодня суббота, а значит нетрезво пора отдать дань волшебному горшочку «Смарт-Лаба», в благодарность за тексты, которые пока еще меня хоть немного, но цепляют.
Выборы в США, война на Кавказе, COVID-19… Б-г дал нам деньги, рынки, и саморазвитие. Куда ты катишься несчастный Смарт-Лаб?

Навыки программирования должны быть у любых современных джентльменов и леди. Это сродни знанию английского, или герменевтике — путь в отдельный мир, живущий по своим законам и правилам. Раз запущенные в голову эти знания меняют человека в лучшую сторону. В сторону, где трава зеленей, а заработки выше.
Забавно было смотреть, что можно было сделать, когда были ресурсы, навыки, полноценная семья, кружки, репетиторы, любая литература. Один раз уже было сделано — работает. Не смотря на хаос, разброд и шатания, преданный тогда импульс и коррекция двигали в верную сторону.
Второй раз будет сложнее. Вроде всего стало больше, но голова уже не такая ясная. Нет зажигающей интеллектуальной яркости, как было ранее, да и энтузиазма стало гораздо меньше. Но стало больше любви, терпения и мудрости. В зеркале поведения своих потомков личные достоинства и недостатки видны гораздо лучше. Тогда я не понимал, что часто сталкиваюсь сам с собой.

( Читать дальше )

"Смартлаб" против "Яндекса"

Если измерить средний уровень интеллекта на ведущем трейдерском сайте России и в ведущей ИТ-компании России, то где он будет выше? 

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


Объявление

    • 01 октября 2020, 18:15
    • |
    • Toddler
  • Еще
Господа программисты! К Вам обращаюсь я...

Опять карантин, опять удаленка… С понедельника придется, по крайней мере, на месяц отключать свою ТС.

Результаты за 4 месяца испытаний следующие:
Объявление
Объявление

( Читать дальше )

....все тэги
UPDONW
Новый дизайн