每个程序员都应该知道的 40 个算法(三)(1)https://developer.aliyun.com/article/1506353
介绍 TensorFlow 的基本概念
让我们简要了解一下 TensorFlow 的概念,比如标量、向量和矩阵。我们知道,在传统数学中,简单的数字,比如三或五,被称为标量。此外,在物理学中,向量是具有大小和方向的东西。在 TensorFlow 中,我们使用向量来表示一维数组。延伸这个概念,二维数组被称为矩阵。对于三维数组,我们使用术语3D 张量。我们使用术语等级来捕捉数据结构的维度。因此,标量是一个等级 0的数据结构,向量是一个等级 1的数据结构,矩阵是一个等级 2的数据结构。这些多维结构被称为张量,并在下图中显示:
在前面的图表中,我们可以看到等级定义了张量的维度。
现在让我们看看另一个参数,shape
。shape
是一个整数元组,指定每个维度中数组的长度。下图解释了shape
的概念:
使用shape
和等级,我们可以指定张量的详细信息。
理解张量数学
现在让我们看看使用张量进行不同的数学计算:
- 让我们定义两个标量,并尝试使用 TensorFlow 进行加法和乘法:
- 我们可以将它们相加和相乘,并显示结果:
- 我们还可以通过将两个张量相加来创建一个新的标量张量:
- 我们还可以执行复杂的张量函数:
理解神经网络的类型
神经网络可以有多种构建方式。如果每一层中的每个神经元都连接到另一层中的每个神经元,那么我们称之为密集或全连接神经网络。让我们看看一些其他形式的神经网络。
卷积神经网络
卷积神经网络(CNNs)通常用于分析多媒体数据。为了更多地了解 CNN 如何用于分析基于图像的数据,我们需要掌握以下过程:
- 卷积
- 池化
让我们逐一探索它们。
卷积
卷积的过程通过使用另一个较小的图像(也称为过滤器或核)来处理特定图像中感兴趣的模式。例如,如果我们想要在图像中找到物体的边缘,我们可以使用特定的过滤器对图像进行卷积来得到它们。边缘检测可以帮助我们进行物体检测、物体分类和其他应用。因此,卷积的过程是关于在图像中找到特征和特点。
寻找模式的方法是基于寻找可以在不同数据上重复使用的模式。可重复使用的模式称为过滤器或核。
池化
为了进行机器学习的多媒体数据处理的重要部分是对其进行下采样。这提供了两个好处:
- 它减少了问题的整体维度,大大减少了训练模型所需的时间。
- 通过聚合,我们可以提取多媒体数据中不必要的细节,使其更通用并更具代表性。
下采样的执行如下:
请注意,我们已经用一个像素替换了每个四个像素的块,选择了四个像素中的最高值作为该像素的值。这意味着我们已经按四分之一的比例进行了下采样。由于我们选择了每个块中的最大值,这个过程被称为最大池化。我们也可以选择平均值;在那种情况下,它将是平均池化。
循环神经网络
循环神经网络(RNNs)是一种特殊类型的神经网络,它们基于循环架构。这就是为什么它们被称为循环。需要注意的重要事情是 RNNs 具有记忆。这意味着它们有能力存储最近迭代的信息。它们被用于分析句子结构以预测句子中的下一个单词等领域。
生成对抗网络
生成对抗网络(GANs)是一种生成合成数据的神经网络类型。它们是由 Ian Goodfellow 及其同事于 2014 年创建的。它们可以用来生成从未存在过的人的照片。更重要的是,它们用于生成合成数据以增加训练数据集。
在接下来的部分中,我们将看到什么是迁移学习。
迁移学习
多年来,许多组织、研究团体和开源社区内的个人已经完善了一些使用大量数据进行训练的复杂模型,以供通用用途。在某些情况下,他们已经投入了多年的努力来优化这些模型。一些这些开源模型可以用于以下应用:
- 视频中的物体检测
- 图像中的物体检测
- 音频的转录
- 文本的情感分析
每当我们开始训练一个新的机器学习模型时,我们要问自己的问题是:我们是否可以简单地定制一个经过充分验证的预训练模型,而不是从头开始?换句话说,我们是否可以将现有模型的学习迁移到我们的自定义模型,以便回答我们的业务问题?如果我们能做到这一点,它将提供三个好处:
- 我们的模型训练工作将得到一个快速启动。
- 通过使用经过充分测试和建立的模型,我们的模型整体质量可能会得到提高。
- 如果我们没有足够的数据来解决我们正在处理的问题,使用通过迁移学习的预训练模型可能会有所帮助。
让我们看两个实际例子,这将是有用的:
- 在训练机器人时,我们可以首先使用模拟游戏来训练神经网络模型。在那个模拟中,我们可以创建所有那些在现实世界中很难找到的罕见事件。一旦训练完成,我们可以使用迁移学习来训练模型适用于真实世界。
- 假设我们想要训练一个模型,可以从视频源中分类苹果和 Windows 笔记本电脑。已经有成熟的开源目标检测模型可以准确分类视频源中的各种物体。我们可以使用这些模型作为起点,识别笔记本电脑。一旦我们识别出物体是笔记本电脑,我们可以进一步训练模型区分苹果和 Windows 笔记本电脑。
在下一节中,我们将应用本章涵盖的概念来构建一个欺诈文档分类神经网络。
案例研究-使用深度学习进行欺诈检测
使用机器学习(ML)技术识别欺诈文档是一个活跃且具有挑战性的研究领域。研究人员正在调查神经网络的模式识别能力在多大程度上可以用于这个目的。可以使用原始像素而不是手动属性提取器,用于几种深度学习架构结构。
方法论
本节介绍的技术使用了一种称为Siamese 神经网络的神经网络架构,它具有两个共享相同架构和参数的分支。使用 Siamese 神经网络来标记欺诈文档如下图所示:
当需要验证特定文档的真实性时,我们首先基于其布局和类型对文档进行分类,然后将其与预期的模板和模式进行比较。如果偏离超过一定阈值,它被标记为伪造文档;否则,它被视为真实文档。对于关键用例,我们可以添加一个手动流程,用于边界情况,算法无法确定地将文档分类为真实或伪造。
为了比较文档与其预期模板,我们在 Siamese 架构中使用两个相同的 CNN。CNN 具有学习最佳的平移不变局部特征检测器和可以构建对输入图像的几何失真具有鲁棒性的表示的优势。这非常适合我们的问题,因为我们的目标是通过单个网络传递真实和测试文档,然后比较它们的相似性。为了实现这个目标,我们实施以下步骤。
假设我们想要测试一个文档。对于每类文档,我们执行以下步骤:
- 获取真实文档的存储图像。我们称之为真实文档。测试文档应该看起来像真实文档。
- 真实文档通过神经网络层,创建一个特征向量,这是真实文档模式的数学表示。我们称之为特征向量 1,如前图所示。
- 需要测试的文档称为测试文档。我们通过一个类似于用于创建真实文档特征向量的网络来传递这个文档。测试文档的特征向量称为特征向量 2。
- 我们使用特征向量 1 和特征向量 2 之间的欧氏距离来计算真实文档和测试文档之间的相似度分数。这个相似度分数被称为相似度测量(MOS)。MOS 是 0 到 1 之间的数字。较高的数字代表文档之间的距离较小,文档相似的可能性较大。
- 如果神经网络计算的相似度分数低于预定义的阈值,我们将文档标记为欺诈。
让我们看看如何使用 Python 实现 Siamese 神经网络:
- 首先,让我们导入所需的 Python 包:
import random import numpy as np import tensorflow as tf
- 接下来,我们将定义将用于处理 Siamese 网络各个分支的神经网络:
def createTemplate(): return tf.keras.models.Sequential([ tf.keras.layers.Flatten(), tf.keras.layers.Dense(128, activation='relu'), tf.keras.layers.Dropout(0.15), tf.keras.layers.Dense(128, activation='relu'), tf.keras.layers.Dropout(0.15), tf.keras.layers.Dense(64, activation='relu'), ])
请注意,为了减少过拟合,我们还指定了0.15
的丢失率。
- 为了实现 Siamese 网络,我们将使用 MNIST 图像。MNIST 图像非常适合测试我们的方法的有效性。我们的方法包括以每个样本包含两个图像和一个二进制相似度标志的方式准备数据。这个标志是它们来自相同类别的指示器。现在让我们实现名为
prepareData
的函数,它可以为我们准备数据:
def prepareData(inputs: np.ndarray, labels: np.ndarray): classesNumbers = 10 digitalIdx = [np.where(labels == i)[0] for i in range(classesNumbers)] pairs = list() labels = list() n = min([len(digitalIdx[d]) for d in range(classesNumbers)]) - 1 for d in range(classesNumbers): for i in range(n): z1, z2 = digitalIdx[d][i], digitalIdx[d][i + 1] pairs += [[inputs[z1], inputs[z2]]] inc = random.randrange(1, classesNumbers) dn = (d + inc) % classesNumbers z1, z2 = digitalIdx[d][i], digitalIdx[dn][i] pairs += [[inputs[z1], inputs[z2]]] labels += [1, 0] return np.array(pairs), np.array(labels, dtype=np.float32)
注意,prepareData()
将导致所有数字的样本数量相等。
- 我们现在将准备训练和测试数据集:
(x_train, y_train), (x_test, y_test) = tf.keras.datasets.mnist.load_data() x_train = x_train.astype(np.float32) x_test = x_test.astype(np.float32) x_train /= 255 x_test /= 255 input_shape = x_train.shape[1:] train_pairs, tr_labels = prepareData(x_train, y_train) test_pairs, test_labels = prepareData(x_test, y_test)
- 现在,让我们创建 Siamese 系统的两个部分:
input_a = tf.keras.layers.Input(shape=input_shape) enconder1 = base_network(input_a) input_b = tf.keras.layers.Input(shape=input_shape) enconder2 = base_network(input_b)
- 现在,我们将实现相似度度量(MOS),它将量化我们想要比较的两个文档之间的距离:
distance = tf.keras.layers.Lambda( lambda embeddings: tf.keras.backend.abs(embeddings[0] - embeddings[1])) ([enconder1, enconder2]) measureOfSimilarity = tf.keras.layers.Dense(1, activation='sigmoid') (distance)
现在,让我们训练模型。我们将使用 10 个 epochs 来训练这个模型:
请注意,我们使用 10 个 epochs 达到了 97.49%的准确率。增加 epochs 的数量将进一步提高准确度水平。
总结
在本章中,我们首先看了神经网络的细节。我们首先看了神经网络多年来的发展。我们研究了不同类型的神经网络。然后,我们看了神经网络的各种构建模块。我们深入研究了用于训练神经网络的梯度下降算法。我们讨论了各种激活函数,并研究了激活函数在神经网络中的应用。我们还看了迁移学习的概念。最后,我们看了一个实际例子,说明了神经网络如何用于训练可以部署到标记伪造或欺诈文件的机器学习模型。
展望未来,在下一章中,我们将探讨如何将这样的算法用于自然语言处理。我们还将介绍网络嵌入的概念,并将研究循环网络在自然语言处理中的应用。最后,我们还将研究如何实现情感分析。
第九章:自然语言处理算法
本章介绍了自然语言处理(NLP)的算法。本章从理论到实践逐步进行。它将首先介绍 NLP 的基础知识,然后介绍基本算法。然后,它将研究最流行的神经网络之一,该网络被广泛用于设计和实施文本数据的重要用例的解决方案。最后,我们将研究 NLP 的局限性,最后学习如何使用 NLP 来训练一个可以预测电影评论极性的机器学习模型。
本章将包括以下部分:
- 介绍 NLP
- 基于词袋(BoW)的 NLP
- 词嵌入介绍
- 使用递归神经网络进行 NLP
- 使用 NLP 进行情感分析
- 案例研究:电影评论情感分析
通过本章结束时,您将了解用于 NLP 的基本技术。您应该能够理解 NLP 如何用于解决一些有趣的现实世界问题。
让我们从基本概念开始。
介绍 NLP
NLP 用于研究形式化和规范化计算机与人类(自然)语言之间的交互。NLP 是一个综合性的学科,涉及使用计算机语言学算法和人机交互技术和方法来处理复杂的非结构化数据。NLP 可以用于各种情况,包括以下情况:
- 主题识别:发现文本存储库中的主题,并根据发现的主题对存储库中的文档进行分类
- 情感分析:根据文本中包含的积极或消极情感对文本进行分类
- 机器翻译:将文本从一种口头人类语言翻译成另一种口头人类语言
- 文本转语音:将口头语言转换为文本
- 主观解释:智能地解释问题并利用可用信息回答问题
- 实体识别:从文本中识别实体(如人、地点或物品)
- 假新闻检测:根据内容标记假新闻
让我们首先看一些在讨论 NLP 时使用的术语。
理解 NLP 术语
NLP 是一个综合性的学科。在围绕某一领域的文献中,我们会观察到,有时会使用不同的术语来指定相同的事物。我们将从一些与 NLP 相关的基本术语开始。让我们从规范化开始,这是一种基本的 NLP 处理,通常在输入数据上执行。
规范化
规范化是对输入文本数据进行的处理,以提高其在训练机器学习模型的情况下的质量。规范化通常包括以下处理步骤:
- 将所有文本转换为大写或小写
- 去除标点符号
- 去除数字
请注意,尽管通常需要前面的处理步骤,但实际的处理步骤取决于我们想要解决的问题。它们会因用例而异,例如,如果文本中的数字代表了在我们尝试解决的问题的情境中可能具有一些价值的东西,那么我们在规范化阶段可能就不需要从文本中去除数字。
语料库
我们用来解决问题的输入文档组称为语料库。语料库充当 NLP 问题的输入数据。
标记化
当我们使用 NLP 时,第一项工作是将文本分成一个标记列表。这个过程称为标记化。由于目标的不同,生成的标记的粒度也会有所不同,例如,每个标记可以包括以下内容:
- 一个词
- 一组单词的组合
- 一个句子
- 一个段落
命名实体识别
在 NLP 中,有许多用例需要从非结构化数据中识别特定的单词和数字,这些单词和数字属于预定义的类别,如电话号码、邮政编码、姓名、地点或国家。这用于为非结构化数据提供结构。这个过程称为命名实体识别(NER)。
停用词
在单词级别的标记化之后,我们得到了文本中使用的单词列表。其中一些单词是常见单词,预计几乎会出现在每个文档中。这些单词不会为它们出现在的文档提供任何额外的见解。这些单词被称为停用词。它们通常在数据处理阶段被移除。一些停用词的例子是was、we和the。
情感分析
情感分析,或者称为意见挖掘,是从文本中提取正面或负面情感的过程。
词干提取和词形还原
在文本数据中,大多数单词可能以稍微不同的形式存在。将每个单词减少到其原始形式或词干所属的词族中称为词干提取。它用于根据它们的相似含义对单词进行分组,以减少需要分析的单词总数。基本上,词干提取减少了问题的整体条件性。
例如,{use, used, using, uses} => use。
英语词干提取的最常见算法是波特算法。
词干提取是一个粗糙的过程,可能会导致词尾被截断。这可能导致拼写错误的单词。对于许多用例来说,每个单词只是我们问题空间中的一个级别的标识符,拼写错误的单词并不重要。如果需要正确拼写的单词,那么应该使用词形还原而不是词干提取。
算法缺乏常识。对于人类大脑来说,将类似的单词视为相同是很简单的。对于算法,我们必须引导它并提供分组标准。
从根本上讲,有三种不同的 NLP 实现方法。这三种技术在复杂性方面有所不同,如下所示:
- 基于词袋模型(BoW-based)的 NLP
- 传统的 NLP 分类器
- 使用深度学习进行自然语言处理
NLTK
自然语言工具包(NLTK)是 Python 中处理 NLP 任务最广泛使用的包。NLTK 是用于 NLP 的最古老和最流行的 Python 库之一。NLTK 非常好,因为它基本上为构建任何 NLP 流程提供了一个起点,它为您提供了基本工具,然后您可以将它们链接在一起以实现您的目标,而不是从头开始构建所有这些工具。许多工具都打包到了 NLTK 中,在下一节中,我们将下载该包并探索其中的一些工具。
让我们来看看基于词袋模型的 NLP。
基于词袋模型的 NLP
将输入文本表示为一组标记的过程称为基于词袋模型的处理。使用词袋模型的缺点是我们丢弃了大部分语法和标记化,这有时会导致丢失单词的上下文。在词袋模型的方法中,我们首先量化要分析的每个文档中每个单词的重要性。
从根本上讲,有三种不同的方法来量化每个文档中单词的重要性:
- 二进制:如果单词出现在文本中,则特征的值为 1,否则为 0。
- 计数:特征将以单词在文本中出现的次数作为其值,否则为 0。
- 词项频率/逆文档频率:特征的值将是单个文档中单词的独特程度与整个文档语料库中单词的独特程度的比率。显然,对于常见单词,如 the、in 等(称为停用词),词项频率-逆文档频率(TF-IDF)得分将很低。对于更独特的单词,例如领域特定术语,得分将更高。
请注意,通过使用词袋模型,我们丢失了信息——即文本中单词的顺序。这通常有效,但可能会导致准确性降低。
让我们看一个具体的例子。我们将训练一个模型,可以将餐厅的评论分类为负面或正面。输入文件是一个结构化文件,其中评论将被分类为正面或负面。
为此,让我们首先处理输入数据。
处理步骤在下图中定义:
让我们通过以下步骤实现这个处理流程:
- 首先,让我们导入我们需要的包:
import numpy as np import pandas as pd
- 然后我们从
CSV
文件中导入数据集:
- 接下来,我们清理数据:
# Cleaning the texts import re import nltk nltk.download('stopwords') from nltk.corpus import stopwords from nltk.stem.porter import PorterStemmer corpus = [] for i in range(0, 1000): review = re.sub('[^a-zA-Z]', ' ', dataset['Review'][i]) review = review.lower() review = review.split() ps = PorterStemmer() review = [ps.stem(word) for word in review if not word in set(stopwords.words('english'))] review = ' '.join(review) corpus.append(review)
- 现在让我们定义特征(用
y
表示)和标签(用X
表示):
from sklearn.feature_extraction.text import CountVectorizer cv = CountVectorizer(max_features = 1500) X = cv.fit_transform(corpus).toarray() y = dataset.iloc[:, 1].values
- 让我们将数据分成测试数据和训练数据:
from sklearn.model_selection import train_test_split X_train, X_test, y_train, y_test = train_test_split(X, y, test_size = 0.20, random_state = 0)
- 对于训练模型,我们使用朴素贝叶斯算法:
from sklearn.naive_bayes import GaussianNB classifier = GaussianNB() classifier.fit(X_train, y_train)
- 让我们预测测试集的结果:
y_pred = classifier.predict(X_test)
- 混淆矩阵如下所示:
通过观察混淆矩阵,我们可以估计误分类情况。
词嵌入简介
在前面的部分中,我们学习了如何使用词袋模型作为输入文本数据的抽象来执行 NLP。NLP 的一个主要进展是我们能够以密集向量的形式创建单词的有意义的数值表示能力。这种技术称为词嵌入。Yoshua Bengio 首次在他的论文《神经概率语言模型》中引入了这个术语。NLP 问题中的每个词都可以被视为一个分类对象。将每个词映射到表示为向量的数字列表称为词嵌入。换句话说,用于将单词转换为实数的方法称为词嵌入。嵌入的一个区别特征是它使用密集向量,而不是使用传统方法使用稀疏矩阵向量。
使用词袋模型进行 NLP 存在两个基本问题:
- 语义上下文的丢失:当我们对数据进行标记化时,它的上下文就丢失了。一个词可能根据它在句子中的使用位置有不同的含义;当解释复杂的人类表达时,比如幽默或讽刺,这变得更加重要。
- 稀疏输入:当我们进行标记化时,每个单词都成为一个特征。正如我们在前面的例子中看到的,每个单词都是一个特征。这导致了稀疏的数据结构。
一个词的邻域
如何向算法呈现文本数据(特别是单词或词元)的关键见解来自语言学。在词嵌入中,我们关注每个词的邻域,并用它来确定其含义和重要性。一个词的邻域是围绕特定词的一组词。一个词的上下文是由它的邻域决定的。
请注意,在词袋模型中,一个词失去了它的上下文,因为它的上下文来自它所在的邻域。
词嵌入的特性
良好的词嵌入具有以下四个特性:
- 它们是密集的:实际上,嵌入本质上是因子模型。因此,嵌入向量的每个组件代表一个(潜在)特征的数量。通常我们不知道该特征代表什么;但是,我们将有非常少的(如果有的话)零值,这将导致稀疏输入。
- 它们是低维的:嵌入具有预定义的维度(作为超参数选择)。我们之前看到,在 BoW 表示中,我们需要为每个单词输入|V|,因此输入的总大小为|V| * n,其中n是我们用作输入的单词数。使用单词嵌入,我们的输入大小将是d * n,其中d通常在 50 到 300 之间。考虑到大型文本语料库通常远大于 300 个单词,这意味着我们在输入大小上有很大的节省,我们看到这可能导致更小的数据实例总数的更高准确性。
- 它们嵌入领域语义:这个属性可能是最令人惊讶的,但也是最有用的。当正确训练时,嵌入会学习关于其领域的含义。
- 易于泛化:最后,网络嵌入能够捕捉到一般的抽象模式——例如,我们可以对(嵌入的)猫、鹿、狗等进行训练,模型将理解我们指的是动物。请注意,模型从未接受过对羊的训练,但模型仍然会正确分类它。通过使用嵌入,我们可以期望得到正确的答案。
现在让我们探讨一下,我们如何使用 RNN 进行自然语言处理。
使用 RNN 进行 NLP
RNN 是一个具有反馈的传统前馈网络。对 RNN 的一种简单思考方式是,它是一个带有状态的神经网络。RNN 可用于任何类型的数据,用于生成和预测各种数据序列。训练 RNN 模型是关于构建这些数据序列。RNN 可用于文本数据,因为句子只是单词序列。当我们将 RNN 用于 NLP 时,我们可以用它来进行以下操作:
- 在输入时预测下一个单词
- 生成新的文本,遵循文本中已经使用的风格:
还记得导致它们正确预测的单词组合吗?RNN 的学习过程是基于语料库中的文本。它们通过减少预测的下一个单词和实际的下一个单词之间的错误来进行训练。
使用 NLP 进行情感分析
本节介绍的方法是基于对分类高速流推文的使用情况。手头的任务是提取关于所选主题的推文中嵌入的情绪。情感分类实时量化每条推文中的极性,然后聚合所有推文的总情感,以捕捉关于所选主题的整体情感。为了应对 Twitter 流数据的内容和行为带来的挑战,并有效地执行实时分析,我们使用 NLP 使用训练过的分类器。然后将训练过的分类器插入 Twitter 流中,以确定每条推文的极性(积极、消极或中性),然后聚合并确定关于某一主题的所有推文的整体极性。让我们一步一步地看看这是如何完成的。
首先,我们必须训练分类器。为了训练分类器,我们需要一个已经准备好的数据集,其中包含有历史的 Twitter 数据,并且遵循实时数据的模式和趋势。因此,我们使用了来自网站www.sentiment140.com的数据集,该数据集带有一个人工标记的语料库(基于该分析的大量文本集合),其中包含超过 160 万条推文。该数据集中的推文已经被标记为三种极性之一:零表示负面,两表示中性,四表示正面。除了推文文本之外,语料库还提供了推文 ID、日期、标志和推文用户。现在让我们看看在训练分类器之前对实时推文执行的每个操作:
- 首先将推文分割成称为标记的单词(标记化)。
- 标记化的输出创建了一个 BoW,其中包含文本中的单个单词。
- 这些推文进一步通过去除数字、标点和停用词(停用词去除)进行过滤。停用词是非常常见的词,如is、am、are和the。由于它们没有额外的信息,这些词被移除。
- 此外,非字母字符,如*#**@*和数字,使用模式匹配进行删除,因为它们在情感分析的情况下没有相关性。正则表达式用于仅匹配字母字符,其余字符将被忽略。这有助于减少 Twitter 流的混乱。
- 先前阶段的结果被用于词干处理阶段。在这个阶段,派生词被减少到它们的词根-例如,像fish这样的词与fishing和fishes具有相同的词根。为此,我们使用标准 NLP 库,它提供各种算法,如 Porter 词干处理。
- 一旦数据被处理,它被转换成一个称为术语文档矩阵(TDM)的结构。TDM 表示过滤后语料库中每个词的术语和频率。
- 从 TDM 中,推文到达训练过的分类器(因为它经过训练,可以处理推文),它计算每个词的情感极性重要性(SPI),这是一个从-5 到+5 的数字。正负号指定了该特定词所代表的情绪类型,其大小表示情感的强度。这意味着推文可以被分类为正面或负面(参考下图)。一旦我们计算了个别推文的极性,我们将它们的总体 SPI 相加,以找到来源的聚合情感-例如,总体极性大于一表示我们观察时间内推文的聚合情感是积极的。
为了获取实时原始推文,我们使用 Scala 库Twitter4J,这是一个提供实时 Twitter 流 API 包的 Java 库。该 API 要求用户在 Twitter 上注册开发者帐户并填写一些认证参数。该 API 允许您获取随机推文或使用选择的关键词过滤推文。我们使用过滤器来检索与我们选择的关键词相关的推文。
总体架构如下图所示:
情感分析有各种应用。它可以用来分类客户的反馈。政府可以利用社交媒体极性分析来找到他们政策的有效性。它还可以量化各种广告活动的成功。
在接下来的部分,我们将学习如何实际应用情感分析来预测电影评论的情感。
案例研究:电影评论情感分析
让我们使用 NLP 进行电影评论情感分析。为此,我们将使用一些开放的电影评论数据,可在www.cs.cornell.edu/people/pabo/movie-review-data/
上找到:
- 首先,我们将导入包含电影评论的数据集:
import numpy as np import pandas as pd
- 现在,让我们加载电影数据并打印前几行以观察其结构。
df=pd.read_csv("moviereviews.tsv",sep='\t') df.head()
请注意数据集有2000
条电影评论。其中一半是负面的,一半是正面的。
- 现在,让我们开始准备数据集以训练模型。首先,让我们删除数据中的任何缺失值
df.dropna(inplace=True)
- 现在我们需要移除空格。空格不是空的,但需要被移除。为此,我们需要遍历输入
DataFrame
中的每一行。我们将使用.itertuples()
来访问每个字段:
blanks=[] for i,lb,rv in df.itertuples(): if rv.isspace(): blanks.append(i) df.drop(blanks,inplace=True)
请注意,我们已经使用i
,lb
和rv
来索引、标签和评论列。
让我们将数据分割成测试和训练数据集:
- 第一步是指定特征和标签,然后将数据分割成训练集和测试集:
from sklearn.model_selection import train_test_split X = df['review'] y = df['label'] X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=42)
现在我们有测试和训练数据集。
- 现在让我们将数据集分成训练集和测试集:
from sklearn.pipeline import Pipeline from sklearn.feature_extraction.text import TfidfVectorizer from sklearn.naive_bayes import MultinomialNB # Naïve Bayes: text_clf_nb = Pipeline([('tfidf', TfidfVectorizer()), ('clf', MultinomialNB()), ])
请注意,我们正在使用tfidf
来量化集合中数据点的重要性。
接下来,让我们使用朴素贝叶斯算法来训练模型,然后测试训练好的模型。
让我们按照以下步骤来训练模型:
- 现在让我们使用我们创建的测试和训练数据集来训练模型:
text_clf_nb.fit(X_train, y_train)
- 让我们运行预测并分析结果:
# Form a prediction set predictions = text_clf_nb.predict(X_test)
让我们通过打印混淆矩阵来查看模型的性能。我们还将查看精确度、召回率、F1 分数和准确度。
这些性能指标为我们提供了预测质量的度量。准确率为 0.78,现在我们已经成功训练了一个可以预测特定电影评论类型的模型。
摘要
在本章中,我们讨论了与自然语言处理相关的算法。首先,我们研究了与自然语言处理相关的术语。接下来,我们研究了实施自然语言处理策略的 BoW 方法。然后,我们研究了词嵌入的概念以及在自然语言处理中使用神经网络。最后,我们看了一个实际的例子,我们在这一章中使用了开发的概念来根据电影评论的文本来预测情感。通过学习本章内容,用户应该能够将自然语言处理用于文本分类和情感分析。
在下一章中,我们将研究推荐引擎。我们将研究不同类型的推荐引擎以及它们如何用于解决一些现实世界的问题。
每个程序员都应该知道的 40 个算法(三)(3)https://developer.aliyun.com/article/1506359