如何从PySpark MultilayerPerceptronClassifier获取分类概率?

10
我在Python中使用Spark 2.0.1,我的数据集是DataFrame,所以我使用ML库(而不是MLLib)进行机器学习。 我有一个多层感知分类器,只有两个标签。
我的问题是,是否可能不仅获取标签,而且还可以(或仅仅)获取该标签的概率?就像不仅仅是对于每个输入返回0或1,而是像0.95对于0和0.05对于1这样的东西。 如果MLP无法实现此功能,但其他分类器可以,则我可以更改分类器。我之所以只使用MLP是因为我知道它们应该能够返回概率,但我在PySpark中找不到它。
我发现了一个类似的主题, 如何从MultilayerPerceptronClassifier获取分类概率? 但他们使用Java,他们建议的解决方案在Python中不起作用。
谢谢
1个回答

12

实际上,自2.0版本以来,Spark ML中的MLP似乎没有提供分类概率;然而,还有许多其他分类器可以提供,例如逻辑回归朴素贝叶斯决策树随机森林。以下是第一个和最后一个分类器的简短示例:

from pyspark.ml.classification import LogisticRegression, RandomForestClassifier
from pyspark.ml.linalg import Vectors
from pyspark.sql import Row
df = sqlContext.createDataFrame([
     (0.0, Vectors.dense(0.0, 1.0)),
     (1.0, Vectors.dense(1.0, 0.0))], 
     ["label", "features"])
df.show()
# +-----+---------+ 
# |label| features| 
# +-----+---------+ 
# | 0.0 |[0.0,1.0]| 
# | 1.0 |[1.0,0.0]| 
# +-----+---------+

lr = LogisticRegression(maxIter=5, regParam=0.01, labelCol="label")
lr_model = lr.fit(df)

rf = RandomForestClassifier(numTrees=3, maxDepth=2, labelCol="label", seed=42)
rf_model = rf.fit(df)

# test data:
test = sc.parallelize([Row(features=Vectors.dense(0.2, 0.5)),
                       Row(features=Vectors.dense(0.5, 0.2))]).toDF()

lr_result = lr_model.transform(test)
lr_result.show()
# +---------+--------------------+--------------------+----------+
# | features|       rawPrediction|         probability|prediction|
# +---------+--------------------+--------------------+----------+
# |[0.2,0.5]|[0.98941878916476...|[0.72897310704261...|       0.0|
# |[0.5,0.2]|[-0.9894187891647...|[0.27102689295738...|       1.0|  
# +---------+--------------------+--------------------+----------+

rf_result = rf_model.transform(test)
rf_result.show()
# +---------+-------------+--------------------+----------+ 
# | features|rawPrediction|         probability|prediction| 
# +---------+-------------+--------------------+----------+ 
# |[0.2,0.5]|    [1.0,2.0]|[0.33333333333333...|       1.0| 
# |[0.5,0.2]|    [1.0,2.0]|[0.33333333333333...|       1.0| 
# +---------+-------------+--------------------+----------+

对于MLlib,请查看我的答案此处;关于PySpark分类的几个未记录和反直觉的特性,请参见我相关的博客文章


你能解释一下概率列实际上显示的是什么吗?在第一行的lr示例中,0.7289是预测结果等于1的概率吗?如果是这样,为什么预测值是0(而预测概率= 0.2710的行具有预测值= 1)? - gannawag
3
请注意点号(...);这里仅显示了probabilities二维数组的第一个元素,即在第一行中probability[0]具有最大值(因此预测为0.0),而在第二行中(未显示)probability[1]具有最大值,因此预测为1.0。同样,在RF中,两行中probability[1](同样未在上面显示)具有最大值,因此两个预测结果均为类别1。该示例很容易复现,只需使用lr_result.show(truncate=False)查看完整的数组值即可。 - desertnaut
@gannawag 0.7289 是结果为 0.0 的概率(Python 索引从零开始),0.2710 同样如此。 - desertnaut

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接