move logic from hyperopt to freqtrade.strategy

This commit is contained in:
gcarq 2018-06-23 11:13:49 +02:00
parent 3360bf4001
commit c40e6a12d1
3 changed files with 35 additions and 21 deletions

View File

@ -11,7 +11,6 @@ import pickle
import signal
import sys
from argparse import Namespace
from copy import deepcopy
from functools import reduce
from math import exp
from operator import itemgetter
@ -27,25 +26,10 @@ from freqtrade.arguments import Arguments
from freqtrade.configuration import Configuration
from freqtrade.optimize import load_data
from freqtrade.optimize.backtesting import Backtesting
from freqtrade.strategy.interface import IStrategy
logger = logging.getLogger(__name__)
HyperoptStrategy = None
def wrap_strategy(strategy: IStrategy) -> Optional[HyperoptStrategy]:
"""Wraps a given Strategy instance to HyperoptStrategy"""
global HyperoptStrategy
attr = deepcopy(dict(strategy.__class__.__dict__))
# Patch module name to make it compatible with pickle
attr['__module__'] = 'freqtrade.optimize.hyperopt'
HyperoptStrategy = type('HyperoptStrategy', (IStrategy,), attr)
return HyperoptStrategy()
class Hyperopt(Backtesting):
"""
Hyperopt class, this class contains all the logic to run a hyperopt simulation
@ -72,9 +56,6 @@ class Hyperopt(Backtesting):
# check that the reported Σ% values do not exceed this!
self.expected_max_profit = 3.0
# Wrap strategy to make it compatible with pickle
self.analyze.strategy = wrap_strategy(self.analyze.strategy)
# Configuration and data used by hyperopt
self.processed: Optional[Dict[str, Any]] = None

View File

@ -0,0 +1,32 @@
import logging
from copy import deepcopy
from freqtrade.strategy.interface import IStrategy
logger = logging.getLogger(__name__)
def import_strategy(strategy: IStrategy) -> IStrategy:
"""
Imports given Strategy instance to global scope
of freqtrade.strategy and returns an instance of it
"""
# Copy all attributes from base class and class
attr = deepcopy({**strategy.__class__.__dict__, **strategy.__dict__})
# Adjust module name
attr['__module__'] = 'freqtrade.strategy'
name = strategy.__class__.__name__
clazz = type(name, (IStrategy,), attr)
logger.debug(
'Imported strategy %s.%s as %s.%s',
strategy.__module__, strategy.__class__.__name__,
clazz.__module__, strategy.__class__.__name__,
)
# Modify global scope to declare class
globals()[name] = clazz
return clazz()

View File

@ -11,6 +11,7 @@ from collections import OrderedDict
from typing import Optional, Dict, Type
from freqtrade import constants
from freqtrade.strategy import import_strategy
from freqtrade.strategy.interface import IStrategy
@ -83,7 +84,7 @@ class StrategyResolver(object):
strategy = self._search_strategy(path, strategy_name)
if strategy:
logger.info('Using resolved strategy %s from \'%s\'', strategy_name, path)
return strategy
return import_strategy(strategy)
raise ImportError(
"Impossible to load Strategy '{}'. This class does not exist"
@ -100,7 +101,7 @@ class StrategyResolver(object):
"""
# Generate spec based on absolute path
spec = importlib.util.spec_from_file_location('user_data.strategies', module_path)
spec = importlib.util.spec_from_file_location('unknown', module_path)
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module) # type: ignore # importlib does not use typehints