我无法弄清sklearn.pipeline.Pipeline
如何正常工作。
doc中有一些解释。例如,他们的意思是:
使用最终估算器进行转换的管道。
为了使我的问题更清楚,steps
是什么?他们是如何运作的?
修改
感谢答案,我可以让我的问题更清楚:
当我调用管道并传递,作为步骤,两个变换器和一个估算器,例如:
pipln = Pipeline([("trsfm1",transformer_1),
("trsfm2",transformer_2),
("estmtr",estimator)])
当我打电话给你时会发生什么?
pipln.fit()
OR
pipln.fit_transform()
我无法弄清楚估算器如何成为变压器以及如何安装变压器。
答案 0 :(得分:119)
Transformer - 一些具有拟合和变换方法的类,或fit_transform方法。
预测器 - 一些适合和预测方法的类,或fit_predict方法。
管道只是一个抽象的概念,它不是现有的ml算法。通常在ML任务中,您需要在应用最终估算器之前执行原始数据集的不同转换序列(查找要素集,生成新要素,仅选择一些好的要素)。
Here是管道使用的一个很好的例子。 Pipeline为您提供了所有3个转换步骤和结果估算器的单一界面。它封装了内部的变换器和预测器,现在你可以做类似的事情:
vect = CountVectorizer()
tfidf = TfidfTransformer()
clf = SGDClassifier()
vX = vect.fit_transform(Xtrain)
tfidfX = tfidf.fit_transform(vX)
predicted = clf.fit_predict(tfidfX)
# Now evaluate all steps on test set
vX = vect.fit_transform(Xtest)
tfidfX = tfidf.fit_transform(vX)
predicted = clf.fit_predict(tfidfX)
只有:
pipeline = Pipeline([
('vect', CountVectorizer()),
('tfidf', TfidfTransformer()),
('clf', SGDClassifier()),
])
predicted = pipeline.fit(Xtrain).predict(Xtrain)
# Now evaluate all steps on test set
predicted = pipeline.predict(Xtest)
使用管道,您可以轻松地对此元估计器的每个步骤的参数集执行网格搜索。如上面的链接所述。除最后一步之外的所有步骤必须是变换,最后一步可以是变换器或预测器。
回答编辑:
当您致电pipln.fit()
时 - 管道内的每个变压器都将安装在先前变压器的输出上(第一个变压器是在原始数据集上学习的)。最后一个估算器可能是变换器或预测器,只有当你的最后一个估算器是变换器(实现fit_transform,或者单独转换和拟合方法)时,你才能在管道上调用fit_transform(),你可以只在管道上调用fit_predict()或predict()你的最后一个估算器是预测器。所以你不能调用fit_transform或转换管道,最后一步是预测器。
答案 1 :(得分:12)
我认为M0rkHaV有正确的想法。 Scikit-learn的管道类是一个有用的工具,可以将多个不同的变换器与估算器一起封装到一个对象中,这样您只需要调用一次重要的方法(fit()
,predict()
等)。让我们分解两个主要组成部分:
变形金刚是同时实施fit()
和transform()
的类。您可能熟悉某些sklearn预处理工具,例如TfidfVectorizer
和Binarizer
。如果您查看这些预处理工具的文档,您会看到它们实现了这两种方法。我觉得非常酷的是,一些估算器也可以用作转换步骤,例如LinearSVC
<!/ p>
Estimators 是同时实现fit()
和predict()
的类。您会发现许多分类器和回归模型都实现了这两种方法,因此您可以轻松地测试许多不同的模型。可以使用另一个变换器作为最终估计器(即,它不一定实现predict()
,但绝对实现fit()
)。所有这些意味着您将无法拨打predict()
。
至于你的编辑:让我们来看一个基于文本的例子。使用LabelBinarizer,我们希望将标签列表转换为二进制值列表。
bin = LabelBinarizer() #first we initialize
vec = ['cat', 'dog', 'dog', 'dog'] #we have our label list we want binarized
现在,当二进制化器适合某些数据时,它将具有一个名为classes_
的结构,其中包含变换器“知道”的唯一类。在不调用fit()
的情况下,二进制文件不知道数据是什么样的,因此调用transform()
没有任何意义。如果在尝试拟合数据之前打印出类列表,则会出现这种情况。
print bin.classes_
尝试此操作时出现以下错误:
AttributeError: 'LabelBinarizer' object has no attribute 'classes_'
但是当您将二进制文件放在vec
列表中时
bin.fit(vec)
再试一次
print bin.classes_
我得到以下内容:
['cat' 'dog']
print bin.transform(vec)
现在,在对vec
对象调用transform之后,我们得到以下内容:
[[0]
[1]
[1]
[1]]
对于用作变换器的估算器,让我们使用DecisionTree
分类器作为特征提取器的示例。决策树很多原因很多,但出于我们的目的,重要的是它们能够对树发现的预测有用的功能进行排名。当您在决策树上致电transform()
时,它会获取您的输入数据并找到它认为最重要的功能。因此,您可以将其视为将数据矩阵(n行m列)转换为较小的矩阵(n行x列),其中k列是决策树找到的k个最重要的特征。
答案 2 :(得分:9)
ML算法通常处理表格数据。您可能需要在ML算法之前和之后对该数据进行预处理和后处理。管道是链接这些数据处理步骤的一种方式。
管道是转换数据的一系列步骤。它来自旧的“管道和过滤器”设计模式(例如,您可以想到带有管道“ |”的unix bash命令或重定向运算符“>”)。但是,管道是代码中的对象。因此,您可能为每个过滤器都有一个类(也就是每个管道步骤),然后是另一个类来将这些步骤组合到最终管道中。一些管道可能将其他管道串联或并联组合,具有多个输入或输出,依此类推。我们喜欢将Pipelining Machine Learning视为:
管道(或管道中的步骤)必须具有这两种方法:
也可以调用此方法将两者链接:
Scikit-Learn的“管道和过滤器”设计模式非常漂亮。但是如何将其用于深度学习,AutoML和复杂的生产级管道?
Scikit-Learn于2007年首次发布,当时是pre deep learning era。但是,它是最著名和采用最广泛的机器学习库之一,并且仍在不断发展。最重要的是,它使用“管道和过滤器”设计模式作为软件架构样式-这就是Scikit-Learn如此出色的原因,此外,它还提供了可供使用的算法。但是,在执行以下操作时会遇到很多问题,我们应该能够在2020年做到这一点:
可以肯定,Scikit-Learn非常方便且结构精良。但是,它需要刷新。这是我们使用Neuraxle的解决方案,使Scikit-Learn在现代计算项目中变得新鲜且可用!
注意:如果管道的某个步骤不需要使用fit或transform方法之一,则可以从NonFittableMixin或NonTransformableMixin继承以提供其中之一的默认实现什么都不做的方法。
首先,管道或其步骤也可以可选地定义这些方法:
默认情况下,提供了以下以下方法以允许管理超参数:
RandInt(1, 3)
,表示1到3层。您可以在此字典上调用.rvs()
以随机选择一个值,然后将其发送到“ set_hyperparams”以尝试对其进行训练。有关建议的解决方案的更多信息,请阅读上面带有链接的大列表中的条目。