преобразование pandas в массив numpy для конвейера sklearn

#python #numpy #scikit-learn #converter #pipeline

#python #numpy #scikit-learn #конвертеры #конвейер

Вопрос:

У меня есть преобразователь, который вычисляет процент значений для каждой группы. Изначально использовался pandas, потому что я начал с pandas, а с именами столбцов удобнее обращаться. Однако теперь мне нужно интегрироваться в sklearn-pipeline.

Как я могу преобразовать свой Transformer для поддержки массивов numpy из конвейера sklearn вместо фреймов данных pandas? Дело в том, что self.colname это нельзя использовать для массивов numpy, и я думаю, что группировку нужно выполнять по-другому.

Как реализовать постоянство такого преобразователя, поскольку эти веса должны быть загружены с диска, чтобы развернуть такой преобразователь в конвейере.

 class PercentageTransformer(TransformerMixin):
    def __init__(self, colname,typePercentage='totalTarget', _target='TARGET', _dropOriginal=True):
        self.colname = colname
        self._target = _target
        self._dropOriginal = _dropOriginal
        self.typePercentage = typePercentage

    def fit(self, X, y, *_):
        original = pd.concat([y,X], axis=1)
        grouped = original.groupby([self.colname, self._target]).size()
        if self.typePercentage == 'totalTarget':
            df = grouped / original[self._target].sum()
        else:
            df = (grouped / grouped.groupby(level=0).sum())

        if self.typePercentage == 'totalTarget':
            nameCol = "pre_"   self.colname
        else:
            nameCol = "pre2_"   self.colname
        self.nameCol = nameCol
        grouped = df.reset_index(name=nameCol)
        groupedOnly = grouped[grouped[self._target] == 1]
        groupedOnly = groupedOnly.drop(self._target, 1)

        self.result =  groupedOnly
        return self

    def transform(self, dataF):
        mergedThing = pd.merge(dataF, self.result, on=self.colname, how='left')
        mergedThing.loc[(mergedThing[self.nameCol].isnull()), self.nameCol] = 0
        if self._dropOriginal:
            mergedThing = mergedThing.drop(self.colname, 1)
        return mergedThing
  

Он будет использоваться в конвейере, подобном этому:

 pipeline =  Pipeline([
    ('features', FeatureUnion([
        ('continuous', Pipeline([
            ('extract', ColumnExtractor(CONTINUOUS_FIELDS)),
        ])),
        ('factors', Pipeline([
            ('extract', ColumnExtractor(FACTOR_FIELDS)),
            # using labelencoding and all bias
            ('bias',  PercentageAllTransformer(FACTOR_FIELDS, _dropOriginal=True, typePercentage='totalTarget')),
        ]))
    ], n_jobs=-1)),
    ('estimator', estimator)
])
  

pipeline Будет оснащен X и y , где оба являются фреймами данных. Я не уверен, что X.as_matrix помогло бы.

Комментарии:

1. pandas объекты являются оболочками вокруг numpy объектов. Я полагаю, вы имеете в виду, что pandas массива нет Series ? В любом случае, возможно, ваша проблема была бы решена простым возвратом self.values вместо self .

2. Что касается постоянства, есть несколько способов добиться этого. Как правило, для сериализации объектов в Python будет использоваться pickle модуль.

3. Действительно, я имел в виду фреймы данных pandas. Дело в том, что, если я правильно понимаю: orignal original.groupby([self.colname, self._target] больше не является фреймом данных, а массивом numpy, например, имена столбцов больше не работают. таким образом, self.values, похоже, недостаточно.

4. Нет, groupby возвращает groupby объект, который обычно используется для генерации нового DataFrame . Вы не можете получить доступ self.colname, self._target , как обычно, потому что по умолчанию они используются как index к новому DataFrame . Передайте as_index=False в groupby , чтобы сохранить столбцы вашей группировки в качестве столбцов.

Ответ №1:

  • Преобразование туда и обратно

В Pandas есть метод .to_records() и, как вы упомянули, метод .as_matrix(). Метод .to_records () фактически сохранит имена ваших столбцов для вас. Numpy поддерживает именованные столбцы в массивах. Смотрите здесь.

  • Постоянство

В Pandas есть метод pandas.to_pickle(obj, filename), который принимает объект pandas и обрабатывает его. Существует соответствующий метод pandas.read_pickle(filename).

В Numpy также есть функции сохранения и загрузки.