Применение IndexToString к вектору объектов в Spark

Контекст: У меня есть фрейм данных, где все категориальные значения были проиндексированы с использованием StringIndexer.

val categoricalColumns = df.schema.collect { case StructField(name, StringType, nullable, meta) => name }    

val categoryIndexers = categoricalColumns.map {
  col => new StringIndexer().setInputCol(col).setOutputCol(s"${col}Indexed") 
}

Затем я использовал VectorAssembler для векторизации всех столбцов объектов (включая индексированные категориальные).

val assembler = new VectorAssembler()
    .setInputCols(dfIndexed.columns.diff(List("label") ++ categoricalColumns))
    .setOutputCol("features")

После применения классификатора и нескольких дополнительных шагов я получаю фрейм данных, который имеет метку, характеристики и прогноз. Я хотел бы расширить вектор объектов на отдельные столбцы, чтобы преобразовать индексированные значения обратно в их исходную строковую форму.

val categoryConverters = categoricalColumns.zip(categoryIndexers).map {
colAndIndexer => new IndexToString().setInputCol(s"${colAndIndexer._1}Indexed").setOutputCol(colAndIndexer._1).setLabels(colAndIndexer._2.fit(df).labels)
}

Вопрос: Есть липросто способ сделать это, или это лучший способ каким-то образом прикрепить столбец прогнозирования к фрейму тестовых данных?

Что я пробовал:

val featureSlicers = categoricalColumns.map {
  col => new VectorSlicer().setInputCol("features").setOutputCol(s"${col}Indexed").setNames(Array(s"${col}Indexed"))
}

Применение этого дает мне столбцы, которые я хочу, но они в векторной форме (как это и должно быть), а не типа Double.

Редактировать: Желаемый вывод - это исходный фрейм данных (т. Е. Категорическое свойство, res как строка, а не индекс) с дополнительным столбцом, указывающим прогнозируемую метку (которая в моем случае равна 0 или 1).

Например, скажем, вывод моего классификатора выглядел примерно так:

+-----+---------+----------+
|label| features|prediction|
+-----+---------+----------+
|  1.0|[0.0,3.0]|       1.0|
+-----+---------+----------+

Применяя VectorSlicer к каждой функции, я получу:

+-----+---------+----------+-------------+-------------+
|label| features|prediction|statusIndexed|artistIndexed|
+-----+---------+----------+-------------+-------------+
|  1.0|[0.0,3.0]|       1.0|        [0.0]|        [3.0]|
+-----+---------+----------+-------------+-------------+

Что здорово, но мне нужно:

+-----+---------+----------+-------------+-------------+
|label| features|prediction|statusIndexed|artistIndexed|
+-----+---------+----------+-------------+-------------+
|  1.0|[0.0,3.0]|       1.0|         0.0 |         3.0 |
+-----+---------+----------+-------------+-------------+

Чтобы затем иметь возможность использовать IndexToString и преобразовать его в:

+-----+---------+----------+-------------+-------------+
|label| features|prediction|    status   |    artist   |
+-----+---------+----------+-------------+-------------+
|  1.0|[0.0,3.0]|       1.0|        good |  Pink Floyd |
+-----+---------+----------+-------------+-------------+

или даже:

+-----+----------+-------------+-------------+
|label|prediction|    status   |    artist   |
+-----+----------+-------------+-------------+
|  1.0|       1.0|        good |  Pink Floyd |
+-----+----------+-------------+-------------+

Ответы на вопрос(1)

Ваш ответ на вопрос