Обработка невидимой категориальной строки Spark CountVectorizer

Я видел, что StringIndexer имеет проблемы с невидимыми ярлыками (см. здесь).

Мой вопрос:

  1. Есть ли у CountVectorizer такое же ограничение? Как он обрабатывает строку, которой нет в словаре?

  2. Кроме того, влияют ли входные данные на размер словаря или он фиксируется в соответствии с параметром размера словаря?

  3. Наконец, с точки зрения машинного обучения, если предположить, что существует простой классификатор, такой как логистическая регрессия, не следует ли невидимую категорию закодировать как строку нулей, чтобы ее можно было рассматривать как «неизвестную», чтобы получить какой-то прогноз по умолчанию?


person Hanan Shteingart    schedule 17.09.2016    source источник


Ответы (1)


Есть ли у CountVectorizer такое же ограничение? Как он обрабатывает строку, отсутствующую в словаре?

Его не волнуют невидимые ценности.

зависит ли размер словаря от входных данных или он фиксирован в соответствии с параметром размера словаря?

Размер вектора не может превышать размер словаря и дополнительно ограничен количеством различных значений.

не следует закодировать невидимую категорию как строку нулей, чтобы рассматривать ее как "неизвестную", чтобы получить некоторые

Именно это и происходит. Однако проблема несколько сложнее. StringIndexer обычно сочетается с OneHotEncoder, который по умолчанию кодирует базовую категорию как вектор нулей, чтобы избежать ловушки фиктивной переменной. Поэтому использование того же подхода с индексацией было бы неоднозначным.

Чтобы проиллюстрировать все это, рассмотрим следующий пример:

import org.apache.spark.ml.feature.CountVectorizer

val train = Seq(Seq("foo"), Seq("bar")).toDF("text")
val test = Seq(Seq("foo"), Seq("foobar")).toDF("text")

// 
val vectorizer = new CountVectorizer().setInputCol("text")

vectorizer.setVocabSize(1000).fit(train).vocabulary
// Array[String] = Array(foo, bar)

/* Vocabulary size is truncated to the value 
provided by VocabSize Param */

vectorizer.setVocabSize(1).fit(train).vocabulary
// Array[String] = Array(bar)

/* Unseen values are ignored and if there are no known values
we get vector of zeros ((2,[],[])) */

vectorizer.setVocabSize(1000).fit(train).transform(test).show
// +--------+---------------------------+
// |    text|cntVec_0a49b1315206__output|
// +--------+---------------------------+
// |   [foo]|              (2,[1],[1.0])|
// |[foobar]|                  (2,[],[])|
// +--------+---------------------------+
person zero323    schedule 17.09.2016
comment
Спасибо @ zero323, вы всегда отвечаете на мои вопросы :-) Один комментарий: размер словаря не фиксированный по параметру vocabSize, это min(distinct(values), vocabSize). - person Hanan Shteingart; 19.09.2016