TypeError: wrapper () принимает 1 позиционный аргумент, но 2 - PullRequest
0 голосов
/ 19 января 2020

Я пытаюсь использовать оптимизатор обучения sci-kit, но у меня возникают некоторые проблемы, которые я не могу решить. Я пытаюсь использовать байесовскую оптимизацию для настройки моих гиперпараметров для моего DNN LSTM. Любая помощь будет в значительной степени оценена. Это мой код.

from skopt.space import Integer, Categorical, Real
from skopt.utils import use_named_args
from skopt import gp_minimize
import tensorflow
import keras.backend as K
import GetPrediction
import Model

dim_learning_rate = Real(low=1e-4, high=1e-2, prior='log-uniform',
                         name='learning_rate')
dim_num_dense_layers = Integer(low=1, high=5, name='num_dense_layers')
dim_num_input_nodes = Integer(low=16, high=128, name='num_input_nodes')
dim_num_dense_nodes = Integer(low=8, high=64, name='num_dense_nodes')
dim_dropout = Real(low=0.01, high=2, name='dropout')
dim_activation = Categorical(categories=['relu', 'sigmoid'],
                             name='activation')
dim_batch_size = Integer(low=1, high=128, name='batch_size')
dim_adam_decay = Real(low=1e-6, high=1e-2, name="adam_decay")

dimensions = [dim_learning_rate,
              dim_num_dense_layers,
              dim_num_input_nodes,
              dim_num_dense_nodes,
              dim_dropout,
              dim_activation,
              dim_batch_size,
              dim_adam_decay
              ]
default_parameters = [1e-3, 1, 512, 13, 0.5, 'relu', 64, 1e-3]


class Optimize:
    def __init__(self, _STOCK, _INTERVAL, _TYPE):
        self.stock = _STOCK
        self.interval = _INTERVAL
        self._type = _TYPE

    @use_named_args(dimensions=dimensions)
    def fitness(self, learning_rate, num_dense_layers, num_input_nodes,
                num_dense_nodes, dropout, activation, batch_size, rms_decay):
        model = Model.Tuning_Model(learning_rate=learning_rate,
                                   num_dense_layers=num_dense_layers,
                                   num_input_nodes=num_input_nodes,
                                   num_dense_nodes=num_dense_nodes,
                                   dropout=dropout,
                                   activation=activation,
                                   rms_decay=rms_decay
                                   )

        Train_Closing, \
        Train_Volume, \
        Train_Labels, \
        Test_Closing, \
        Test_Volume, \
        Test_Labels, \
        ClosingData_scaled, \
        VolumeData_scaled = GetPrediction.Return_Data(self.stock, self.interval, self._type)

        # named blackbox becuase it represents the structure
        blackbox = model.fit(
            [
                Train_Closing,
                Train_Volume
            ],
            [
                Train_Labels
            ],
            validation_data=(
                [
                    Test_Closing,
                    Test_Volume
                ],
                [
                    Test_Labels
                ]
            ),
            epochs=250,
            batch_size=batch_size
        )
        # return the validation accuracy for the last epoch.
        accuracy = blackbox.history['val_mae'][-1]

        # Delete the Keras model with these hyper-parameters from memory.
        del model

        # Clear the Keras session, otherwise it will keep adding new
        # models to the same TensorFlow graph each time we create
        # a model with a different set of hyper-parameters.
        K.clear_session()
        tensorflow.reset_default_graph()

        # the optimizer aims for the lowest score, so we return our negative accuracy
        return -accuracy

    def Return_BestHyperParameters(self):
        gp_result = gp_minimize(func=self.fitness,
                                dimensions=dimensions,
                                n_calls=12)
        return gp_result


if __name__ == '__main__':
    MyClass = Optimize('DJI', '', 'Daily')
    print(MyClass.Return_BestHyperParameters())

Большая часть кода взята из статьи, которую я недавно прочитал. Вот ошибка.

/home/martin/PycharmProjects/MarketPredictor/venv/lib/python3.6/site-packages/sklearn/externals/joblib/__init__.py:15: FutureWarning: sklearn.externals.joblib is deprecated in 0.21 and will be removed in 0.23. Please import this functionality directly from joblib, which can be installed with: pip install joblib. If this warning is raised when loading pickled models, you may need to re-serialize those models with scikit-learn 0.21+.
  warnings.warn(msg, category=FutureWarning)
/home/martin/PycharmProjects/MarketPredictor/venv/lib/python3.6/site-packages/sklearn/utils/deprecation.py:144: FutureWarning: The sklearn.metrics.scorer module is  deprecated in version 0.22 and will be removed in version 0.24. The corresponding classes / functions should instead be imported from sklearn.metrics. Anything that cannot be imported from sklearn.metrics is now part of the private API.
  warnings.warn(message, FutureWarning)
Using TensorFlow backend.
Traceback (most recent call last):
  File "/home/martin/PycharmProjects/MarketPredictor/Optimizer.py", line 104, in <module>
    print(MyClass.Return_BestHyperParameters())
  File "/home/martin/PycharmProjects/MarketPredictor/Optimizer.py", line 98, in Return_BestHyperParameters
    n_calls=12)
  File "/home/martin/PycharmProjects/MarketPredictor/venv/lib/python3.6/site-packages/skopt/optimizer/gp.py", line 237, in gp_minimize
    n_jobs=n_jobs)
  File "/home/martin/PycharmProjects/MarketPredictor/venv/lib/python3.6/site-packages/skopt/optimizer/base.py", line 248, in base_minimize
    next_y = func(next_x)
TypeError: wrapper() takes 1 positional argument but 2 were given

Process finished with exit code 1

Спасибо всем заранее.

Ответы [ 2 ]

0 голосов
/ 19 января 2020

Ваша проблема возникает, когда func вызывается здесь , что фактически вызывает функцию как func(func.__self__, next_x), потому что ваша функция - bound method. Вот небольшой пример, который воспроизводит проблему:

from functools import wraps

def decorate(func):
    @wraps(func)
    def wrapper(foo):
        func(foo)
    return wrapper

class Foo:
    @decorate
    def bar(self, foo):
        pass

foo = Foo()
foo.bar('foo')

Вместо этого вы можете использовать лямбду:

gp_result = gp_minimize(func=lambda params: self.fitness(params),
                        dimensions=dimensions,
                        n_calls=12)

Или реорганизовать свой код так, чтобы передать данные c метод вместо.

0 голосов
/ 19 января 2020

Минимальный воспроизводимый пример был бы хорош. Но я предполагаю, что проблема в том, что функция, которая должна быть минимизирована, является методом. Поэтому fun c внутри scipy получает два аргумента (self и x). Попробуйте вместо этого:

    def Return_BestHyperParameters(self):
        gp_result = gp_minimize(func=lambda x: self.fitness(x),
                                dimensions=dimensions,
                                n_calls=12)
        return gp_result


Изменить, чтобы соответствовать декоратору:

from skopt.space import Integer, Categorical, Real
from skopt.utils import use_named_args
from skopt import gp_minimize
import tensorflow
import keras.backend as K
import GetPrediction
import Model

dim_learning_rate = Real(low=1e-4, high=1e-2, prior='log-uniform',
                         name='learning_rate')
dim_num_dense_layers = Integer(low=1, high=5, name='num_dense_layers')
dim_num_input_nodes = Integer(low=16, high=128, name='num_input_nodes')
dim_num_dense_nodes = Integer(low=8, high=64, name='num_dense_nodes')
dim_dropout = Real(low=0.01, high=2, name='dropout')
dim_activation = Categorical(categories=['relu', 'sigmoid'],
                             name='activation')
dim_batch_size = Integer(low=1, high=128, name='batch_size')
dim_adam_decay = Real(low=1e-6, high=1e-2, name="adam_decay")

dimensions = [dim_learning_rate,
              dim_num_dense_layers,
              dim_num_input_nodes,
              dim_num_dense_nodes,
              dim_dropout,
              dim_activation,
              dim_batch_size,
              dim_adam_decay
              ]
default_parameters = [1e-3, 1, 512, 13, 0.5, 'relu', 64, 1e-3]


def fitness_wrapper(_STOCK, _INTERVALL, _TYPE):

    @use_named_args(dimensions=dimensions)
    def fitness(self, learning_rate, num_dense_layers, num_input_nodes,
                num_dense_nodes, dropout, activation, batch_size, rms_decay):
        model = Model.Tuning_Model(learning_rate=learning_rate,
                                   num_dense_layers=num_dense_layers,
                                   num_input_nodes=num_input_nodes,
                                   num_dense_nodes=num_dense_nodes,
                                   dropout=dropout,
                                   activation=activation,
                                   rms_decay=rms_decay
                                   )

        Train_Closing, \
        Train_Volume, \
        Train_Labels, \
        Test_Closing, \
        Test_Volume, \
        Test_Labels, \
        ClosingData_scaled, \
        VolumeData_scaled = GetPrediction.Return_Data(self.stock, self.interval, self._type)

        # named blackbox becuase it represents the structure
        blackbox = model.fit(
            [
                Train_Closing,
                Train_Volume
            ],
            [
                Train_Labels
            ],
            validation_data=(
                [
                    Test_Closing,
                    Test_Volume
                ],
                [
                    Test_Labels
                ]
            ),
            epochs=250,
            batch_size=batch_size
        )
        # return the validation accuracy for the last epoch.
        accuracy = blackbox.history['val_mae'][-1]

        # Delete the Keras model with these hyper-parameters from memory.
        del model

        # Clear the Keras session, otherwise it will keep adding new
        # models to the same TensorFlow graph each time we create
        # a model with a different set of hyper-parameters.
        K.clear_session()
        tensorflow.reset_default_graph()

        # the optimizer aims for the lowest score, so we return our negative accuracy
        return -accuracy

    return fitness


def Return_BestHyperParameters(_STOCK, _INTERVALL, _TYPE):
    gp_result = gp_minimize(func=fitness_wrapper(_STOCK, _INTERVALL, _TYPE),
                            dimensions=dimensions,
                            n_calls=12)
    return gp_result


if __name__ == '__main__':
    print(Return_BestHyperParameters(_STOCK="DJI", _INTERVALL="", _TYPE="Daily"))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...