From 985f1868ac457cc60e444f0250d823f628cf8769 Mon Sep 17 00:00:00 2001 From: OtenMoten <32872932+OtenMoten@users.noreply.github.com> Date: Mon, 23 Dec 2019 20:20:55 +0100 Subject: [PATCH] Add Hyperopt file for AverageStrategy --- user_data/hyperopts/AverageHyperopt.py | 148 ++++++++++++++++++ .../berlinguyinca/AverageStrategy.py | 3 - 2 files changed, 148 insertions(+), 3 deletions(-) create mode 100644 user_data/hyperopts/AverageHyperopt.py diff --git a/user_data/hyperopts/AverageHyperopt.py b/user_data/hyperopts/AverageHyperopt.py new file mode 100644 index 0000000..5677b4a --- /dev/null +++ b/user_data/hyperopts/AverageHyperopt.py @@ -0,0 +1,148 @@ +import talib.abstract as ta +from pandas import DataFrame +from typing import Dict, Any, Callable, List +from functools import reduce + +from skopt.space import Categorical, Dimension, Integer, Real + +import freqtrade.vendor.qtpylib.indicators as qtpylib +from freqtrade.optimize.hyperopt_interface import IHyperOpt + +shortRangeBegin = 10 +shortRangeEnd = 40 +mediumRangeBegin = 50 +mediumRangeEnd = 150 + + +class AverageHyperopt(IHyperOpt): + """ + Hyperopt file for optimizing AverageStrategy. + Uses ranges of EMA periods to find the best parameter combination. + """ + + @staticmethod + def populate_indicators(dataframe: DataFrame, metadata: dict) -> DataFrame: + + for short in range(shortRangeBegin, shortRangeEnd): + dataframe[f'maShort({short})'] = ta.EMA(dataframe, timeperiod=short) + + for medium in range(mediumRangeBegin, mediumRangeEnd): + dataframe[f'maMedium({medium})'] = ta.EMA(dataframe, timeperiod=medium) + + return dataframe + + @staticmethod + def buy_strategy_generator(params: Dict[str, Any]) -> Callable: + """ + Define the buy strategy parameters to be used by hyperopt + """ + def populate_buy_trend(dataframe: DataFrame, metadata: dict) -> DataFrame: + """ + Buy strategy Hyperopt will build and use + """ + conditions = [] + + # TRIGGERS + if 'trigger' in params: + for short in range(shortRangeBegin, shortRangeEnd): + for medium in range(mediumRangeBegin, mediumRangeEnd): + if params['trigger'] == f"cross_short({short})_above_medium({medium})": + conditions.append(qtpylib.crossed_above( + dataframe[f'maShort({short})'], dataframe[f'maMedium({medium})'])) + + if conditions: + dataframe.loc[ + reduce(lambda x, y: x & y, conditions), + 'buy'] = 1 + + return dataframe + + return populate_buy_trend + + @staticmethod + def indicator_space() -> List[Dimension]: + """ + Define your Hyperopt space for searching strategy parameters + """ + buyTriggerList = [] + for short in range(shortRangeBegin, shortRangeEnd): + for medium in range(mediumRangeBegin, mediumRangeEnd): + buyTriggerList.append( + f'cross_short({short})_above_medium({medium}') + return [ + Categorical(buyTriggerList, name='trigger') + ] + + @staticmethod + def sell_strategy_generator(params: Dict[str, Any]) -> Callable: + """ + Define the sell strategy parameters to be used by hyperopt + """ + def populate_sell_trend(dataframe: DataFrame, metadata: dict) -> DataFrame: + """ + Sell strategy Hyperopt will build and use + """ + # print(params) + conditions = [] + + # TRIGGERS + if 'sell-trigger' in params: + for short in range(shortRangeBegin, shortRangeEnd): + for medium in range(mediumRangeBegin, mediumRangeEnd): + if params['sell-trigger'] == f'cross_medium({medium})_above_short({short})': + conditions.append(qtpylib.crossed_above( + dataframe[f'maMedium({medium})'], dataframe[f'maShort({short})'])) + + if conditions: + dataframe.loc[ + reduce(lambda x, y: x & y, conditions), + 'sell'] = 1 + + return dataframe + + return populate_sell_trend + + @staticmethod + def sell_indicator_space() -> List[Dimension]: + """ + Define your Hyperopt space for searching sell strategy parameters + """ + sellTriggerList = [] + for short in range(shortRangeBegin, shortRangeEnd): + for medium in range(mediumRangeBegin, mediumRangeEnd): + sellTriggerList.append( + f'cross_medium(medium)_above_short({short})') + + return [ + Categorical(sellTriggerList, name='sell-trigger') + ] + + def populate_buy_trend(self, dataframe: DataFrame, metadata: dict) -> DataFrame: + """ + Based on TA indicators. Should be a copy of from strategy + must align to populate_indicators in this file + Only used when --spaces does not include buy + """ + dataframe.loc[ + ( + qtpylib.crossed_above( + dataframe['maShort'], dataframe['maMedium']) + ), + 'buy'] = 1 + + return dataframe + + def populate_sell_trend(self, dataframe: DataFrame, metadata: dict) -> DataFrame: + """ + Based on TA indicators. Should be a copy of from strategy + must align to populate_indicators in this file + Only used when --spaces does not include sell + """ + dataframe.loc[ + ( + qtpylib.crossed_above( + dataframe['maMedium'], dataframe['maShort']) + ), + 'sell'] = 1 + + return dataframe diff --git a/user_data/strategies/berlinguyinca/AverageStrategy.py b/user_data/strategies/berlinguyinca/AverageStrategy.py index 3a32e90..4765988 100644 --- a/user_data/strategies/berlinguyinca/AverageStrategy.py +++ b/user_data/strategies/berlinguyinca/AverageStrategy.py @@ -1,7 +1,5 @@ # --- Do not remove these libs --- from freqtrade.strategy.interface import IStrategy -from typing import Dict, List -from functools import reduce from pandas import DataFrame # -------------------------------- @@ -32,7 +30,6 @@ class AverageStrategy(IStrategy): ticker_interval = '4h' def populate_indicators(self, dataframe: DataFrame, metadata: dict) -> DataFrame: - macd = ta.MACD(dataframe) dataframe['maShort'] = ta.EMA(dataframe, timeperiod=8) dataframe['maMedium'] = ta.EMA(dataframe, timeperiod=21)