如何使用scikit学习管道简化数据预处理

时间:2018-10-24 21:39:41

标签: python machine-learning scikit-learn

我有2个dfs。 df1是猫的例子,df2是狗的例子。

我必须通过调用不同的函数来对这些df进行一些预处理。我想使用scikit学习管道。

这些功能之一是特殊的编码器功能,该功能将查看df中的列并返回一个特殊值。我在scikit中的我看到正在使用这样的类中重写了该函数:

class Encoder(BaseEstimator, TransformerMixin):

    def __init__(self):
        self.values = []
        super().__init__()

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

    def encode(self,row):
        result = []
        for base in row:
            result.append(bases[base])

        self.values.append(result)

    def transform(self, X):
        assert isinstance(X, pd.DataFrame)
        X["seq_new"].apply(self.encode)

        return self.values

所以现在我将有2个列表:

encode = Encoder()
X1 = encode.transform(df1)
X2 = encode.transform(df2)

下一步将是:

features = np.concatenate((X1, X1), axis=0)

下一步构建标签:

Y_dog = [[1]] * len(X1)
Y_cat = [[0]] * len(X2)
labels = np.concatenate((Y_dog, Y_cat), axis=0)

和其他一些操作,然后我将执行model_selection.train_test_split()将数据拆分为训练和测试。

我如何在scikit管道中调用所有这些功能?我发现的示例从已经完成火车/测试拆分的地方开始。

1 个答案:

答案 0 :(得分:1)

关于sklearn.pipeline.Pipeline的事情是,每个步骤都需要实现fittransform。因此,举例来说,如果您知道您将始终需要执行连接步骤,而您确实渴望将其放入Pipeline(我不会,但这只是我的拙见) ),则需要使用适当的Concatenatorclass方法创建一个fit transform

类似这样的东西:

class Encoder(object):
    def fit(self, X, *args, **kwargs):
        return self
    def transform(self, X):
        return X*2

class Concatenator(object):
    def fit(self, X, *args, **kwargs):
        return self
    def transform(self, Xs):
        return np.concatenate(Xs, axis=0)

class MultiEncoder(Encoder):
    def transform(self, Xs):
        return list(map(super().transform, Xs))

pipe = sklearn.pipeline.Pipeline((
    ("encoder", MultiEncoder()),
    ("concatenator", Concatenator())
))

pipe.fit_transform((
    pd.DataFrame([[1,2],[3,4]]), 
    pd.DataFrame([[5,6],[7,8]])
))