Spark-Scala 中的文本预处理

Text Preprocessing in Spark-Scala

我想对 Spark-Scala 中的大量文本数据应用预处理阶段,例如 Lemmatization - Remove Stop Words(using Tf-Idf) - POS tagging,那里有什么方法可以在 Spark - Scala 中实现它们?

例如,这是我的一个数据样本:

The perfect fit for my iPod photo. Great sound for a great price. I use it everywhere. it is very usefulness for me.

预处理后:

perfect fit iPod photo great sound great price use everywhere very useful

他们有 POS 标签,例如 (iPod,NN) (photo,NN)

有词性标注(sister.arizona)是否适用于 Spark?

一切皆有可能。问题是您更喜欢这样做的方式是什么。

例如,您是否有适合您的停用词词典(它可以只是一个集合),或者您是否希望 运行 TF-IDF 自动选择停用词(注意这需要一些监督,例如选择该词被视为停用词的阈值)。你可以提供字典,还有Spark的MLLib already comes with TF-IDF.

POS 标记步骤很棘手。 JVM 上的大多数 NLP 库(例如 Stanford CoreNLP)未实现 java.io.Serializable,但您可以使用它们执行映射步骤,例如

myRdd.map(functionToEmitPOSTags)

另一方面,不要从该 NLP 库发出包含不可序列化 类 的 RDD,因为 collect()、saveAsNewAPIHadoopFile 等步骤将失败。另外,为了减少序列化带来的麻烦,请使用 Kryo 而不是默认的 Java 序列化。如果您 google 周围有很多关于此问题的帖子,但请参阅 here and here

弄清楚序列化问题后,您需要弄清楚使用哪个 NLP 库来生成 POS 标签。有很多这样的,例如Stanford CoreNLP, LingPipe and Mallet for Java, Epic for Scala, etc. Note that you can of course use the Java NLP libraries with Scala, including with wrappers such as the University of Arizona's Sista wrapper 围绕 Stanford CoreNLP 等

此外,为什么您的示例没有将处理后的文本小写?这几乎是我要做的第一件事。如果您有特殊情况,例如 iPod,您可以使用小壳,除非是那些情况。不过,总的来说,我会小写一切。如果要删除标点符号,您可能应该首先将文本拆分为句子(使用正则表达式等在句点上拆分)。如果您一般要删除标点符号,那当然可以使用正则表达式来完成。

您想阻止多深?例如,Porter 词干分析器(每个 NLP 库中都有实现)的词干是如此之深,以至于 "universe" 和 "university" 成为相同的结果词干。你真的想要那个吗?根据您的用例,那里没有那么激进的词干分析器。此外,如果可以使用词形还原,为什么还要使用词干提取,即将单词拆分为语法前缀、词根和后缀(例如 walked = walk (root) + ed (suffix))。在大多数情况下,根会给你带来比茎更好的结果。我上面提到的大多数 NLP 库都是这样做的。

另外,停用词和无用词之间的区别是什么?例如,您删除了主语形式 "I" 和所有格形式 "my," 中的代词,但没有删除宾语形式 "me." 我建议您选择一本 NLP 教科书,例如 Jurafsky 的 "Speech and Language Processing"和 Martin(对于雄心勃勃的人),或者只是阅读一本以工程为中心的关于 NLP 工具的书籍,例如 LingPipe for Java, NLTK for Python 等,以获得对术语、步骤的良好概述在 NLP 流水线等中

Apache Spark 中没有内置的 NLP 功能。您必须自己实现它,也许基于非分布式 NLP 库,如 marekinfo 的优秀答案中所述。

我建议您看一下 spark ml pipeline。您可能还没有开箱即用,但您可以构建自己的能力并将管道用作框架..