Python: Ошибка вызова метода наследуемого родительского класса - PullRequest
1 голос
/ 12 октября 2019

Я создал сквозную класс-оболочку для существующего класса из sklearn, и он не работает должным образом:

import pandas as pd
from sklearn.preprocessing import OrdinalEncoder

tiny_df = pd.DataFrame({'x': ['a', 'b']})

class Foo(OrdinalEncoder):

    def __init__(self, *args, **kwargs):
        super().__init__(self, *args, **kwargs)

    def fit(self, X, y=None):
        super().fit(X, y)
        return self


oe = OrdinalEncoder()
oe.fit(tiny_df) # works fine
foo = Foo()
foo.fit(tiny_df) # fails

Соответствующая часть сообщения об ошибке, которое я получаю:

~\.conda\envs\pytorch\lib\site-packages\sklearn\preprocessing\_encoders.py in _fit(self, X, handle_unknown)
     69                         raise ValueError("Unsorted categories are not "
     70                                          "supported for numerical categories")
---> 71             if len(self._categories) != n_features:
     72                 raise ValueError("Shape mismatch: if n_values is an array,"
     73                                  " it has to be of shape (n_features,).")

TypeError: object of type 'Foo' has no len()

Каким-то образом закрытое свойство родителя _categories, похоже, не установлено, хотя я вызвал родительский конструктор в методе __init__() моего класса. Я, должно быть, здесь упускаю что-то простое и буду признателен за любую помощь!

1 Ответ

2 голосов
/ 12 октября 2019

Вам не нужно снова передавать self в функцию super. И оценщики scikit-learn всегда должны указывать свои параметры в сигнатуре своих __init__, и varargs не допускается, иначе вы получите RUNTIMEERROR, поэтому вам придется удалить его. Я изменил ваш код, как показано ниже:

import pandas as pd
from sklearn.preprocessing import OrdinalEncoder

tiny_df = pd.DataFrame({'x': ['a', 'b']})

class Foo(OrdinalEncoder):

    def __init__(self, **kwargs):
        super().__init__(**kwargs)

    def fit(self, X, y=None):
        super().fit(X, y)
        return self


oe = OrdinalEncoder()
oe.fit(tiny_df) # works fine
foo = Foo()
foo.fit(tiny_df) # works fine too

ВЫБОР ОБРАЗЦА

foo.transform(tiny_df)
array([[0.],
       [1.]])

Немного больше

class Foo(OrdinalEncoder):

    def __init__(self, *args, **kwargs):
        super().__init__(*args,**kwargs)

    def fit(self, X, y=None):
        super().fit(X, y)
        return self

И когда вы создаете Foo:

foo= Foo()

RuntimeError: scikit-learn estimators should always specify their parameters in the signature of their __init__ (no varargs). <class '__main__.Foo'> with constructor (self, *args, **kwargs) doesn't  follow this convention.

Надеюсь, это поможет!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...