Feature extraction - sklearn文本特征提取

简介:

文本特征提取

词袋(Bag of Words)表征

文本分析是机器学习算法的主要应用领域。但是,文本分析的原始数据无法直接丢给算法,这些原始数据是一组符号,因为大多数算法期望的输入是固定长度的数值特征向量而不是不同长度的文本文件。为了解决这个问题, scikit-learn 提供了一些实用工具可以用最常见的方式从文本内容中抽取数值特征,比如说:

  • 标记(tokenizing) 文本以及为每一个可能的标记(token)分配的一个整型ID ,例如用白空格和标点符号作为标记的分割符(中文的话涉及到分词的问题)
  • 计数(counting) 标记在每个文本中的出现频率
  • 正态化(nomalizating) 降低在大多数样本/文档中都出现的标记的权重

在这个方案中,特征和样本的定义如下:

将 每个标记出现的频率 (无论是否正态化)作为 特征 。

给定 文件 中所有标记的出现频率所构成的向量作为多元 样本 。

因此,语料文件可以用一个词文档矩阵代表,每行是一个文档,每列是一个标记(即词)。

将文档文件转化为数值特征的一般过程被称为 向量化 。这个特殊的策略(标记,计数和正态化)被称为 词袋 或者Bag of n-grams表征。用词频描述文档,但是完全忽略词在文档中出现的相对位置信息。

稀疏性

大多数文档通常只会使用语料库中所有词的一个子集,因而产生的矩阵将有许多特征值是0(通常99%以上都是0)。

例如,一组10,000个短文本(比如email)会使用100,000的词汇总量,而每个文档会使用100到1,000个唯一的词。

为了能够在内存中存储这个矩阵,同时也提供矩阵/向量代数运算的速度,通常会使用稀疏表征例如在scipy.sparse包中提供的表征。

通用向量使用

CountVectorizer 在一个类中实现了标记和计数:

from sklearn.feature_extraction.text import CountVectorizer

这个模型有许多参数,不过默认值已经非常合理(具体细节请见 参考文档 ):

vectorizer = CountVectorizer(min_df=1)
vectorizer
CountVectorizer(analyzer=...'word', binary=False, charset=None,
	charset_error=None, decode_error=...'strict',
	dtype=<... 'numpy.int64'>, encoding=...'utf-8', input=...'content',
	lowercase=True, max_df=1.0, max_features=None, min_df=1,
	ngram_range=(1, 1), preprocessor=None, stop_words=None,
	strip_accents=None, token_pattern=...'(?u)\\b\\w\\w+\\b',
	tokenizer=None, vocabulary=None)

让我们用它来标记和计算一个简单语料的词频:

corpus = [
	'This is the first document.',
	'This is the second second document.',
	'And the third one.',
	'Is this the first document?',
 ]
X = vectorizer.fit_transform(corpus)
X						
<4x9 sparse matrix of type '<... 'numpy.int64'>'
    with 19 stored elements in Compressed Sparse Column format>

默认设置通过抽取2个字符以上的词标记字符。完成这个步骤的具体函数可以直接调用:

analyze = vectorizer.build_analyzer()
analyze("This is a text document to analyze.") == (
     ['this', 'is', 'text', 'document', 'to', 'analyze'])

True

在拟合过程中,每一个分析器找到的词都会分配一个在结果矩阵中对应列的整型索引。列的含义可以用下面的方式获得:

vectorizer.get_feature_names() == (
     ['and', 'document', 'first', 'is', 'one',
      'second', 'the', 'third', 'this'])

True

X.toarray()
array([[0, 1, 1, 1, 0, 0, 1, 0, 1],
       [0, 1, 0, 1, 0, 2, 1, 0, 1],
       [1, 0, 0, 0, 1, 0, 1, 1, 0],
       [0, 1, 1, 1, 0, 0, 1, 0, 1]]...)

特征名称与列索引的转化映射被存储在向量器(vectorizer)的vocabulary_属性中:

vectorizer.vocabulary_.get('document')

1

因此,在训练语料中没有出现的词在后续调用转化方法时将被完全忽略:

vectorizer.transform(['Something completely new.']).toarray()

array([[0, 0, 0, 0, 0, 0, 0, 0, 0]]...)

注意在前面的语料中,第一个和最后一个文档的词完全相同因此被编码为等价的向量。但是,我们丢失了最后一个文档是疑问形式的信息。为了保留一些局部顺序信息,我们可以在抽取词的1-grams(词本身)之外,再抽取2-grams:

bigram_vectorizer = CountVectorizer(ngram_range=(1, 2),
							  token_pattern=r'\b\w+\b', min_df=1)
analyze = bigram_vectorizer.build_analyzer()
analyze('Bi-grams are cool!') == (
	['bi', 'grams', 'are', 'cool', 'bi grams', 'grams are', 'are cool'])
True

因此,由这个向量器抽取的词表非常大,现在可以解决由于局部位置模型编码的歧义问题:

X_2 = bigram_vectorizer.fit_transform(corpus).toarray()
X_2
...                           
array([[0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0],
       [0, 0, 1, 0, 0, 1, 1, 0, 0, 2, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0],
       [1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0],
       [0, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1]]...)

特别是疑问形式“Is this”只出现在最后一个文档:

feature_index = bigram_vectorizer.vocabulary_.get('is this')
X_2[:, feature_index]     

array([0, 0, 0, 1]...)

Tf-idf词权重

在较低的文本语料库中,一些词非常常见(例如,英文中的“the”,“a”,“is”),因此很少带有文档实际内容的有用信息。

目录
相关文章
|
存储 索引
文本特征提取-TfidfVectorizer和CountVectorizer
文本特征提取-TfidfVectorizer和CountVectorizer
239 0
文本特征提取-TfidfVectorizer和CountVectorizer
|
6月前
|
机器学习/深度学习 数据挖掘 API
[FastText in Text Classification]论文实现:Bag of Tricks for Efficient Text Classification
[FastText in Text Classification]论文实现:Bag of Tricks for Efficient Text Classification
36 2
|
测试技术 计算机视觉
sklearn.model_selection.learning_curve介绍(评估多大的样本量用于训练才能达到最佳效果)
sklearn.model_selection.learning_curve介绍(评估多大的样本量用于训练才能达到最佳效果)
|
机器学习/深度学习 存储 数据挖掘
【文本分类】Bag of Tricks for Efficient Text Classification
【文本分类】Bag of Tricks for Efficient Text Classification
【文本分类】Bag of Tricks for Efficient Text Classification
|
机器学习/深度学习 编解码 数据挖掘
A Semisupervised CRF Model for CNN-Based Semantic Segmentation With Sparse Ground Truth
A Semisupervised CRF Model for CNN-Based Semantic Segmentation With Sparse Ground Truth
111 0
A Semisupervised CRF Model for CNN-Based Semantic Segmentation With Sparse Ground Truth
|
机器学习/深度学习 算法 计算机视觉
YOLOv5的Tricks | 【Trick2】目标检测中进行多模型推理预测(Model Ensemble)
在学习yolov5代码的时候,发现experimental.py文件中有一个很亮眼的模块:Ensemble。接触过机器学习的可能了解到,机器学习的代表性算法是随机森林这种,使用多个模型来并行推理,然后归纳他们的中值或者是平均值来最为整个模型的最后预测结构,没想到的是目标检测中也可以使用,叹为观止。下面就对其进行详细介绍:
1437 1
|
存储 人工智能 Python
sklearn中的文本特征提取方法
什么是特征提取? 特征提取就是将一些原始的输入的数据维度减少或者将原始的特征进行重新组合以便于后续的使用。 比如: 我们知道有的时候原始数据的特征很多,而且有的高度相关,有的却又和最终的目的没有关系。我们需要去除没有关系的特征。(减少数据维度) 对于图像来说,每个图像有很多数据,这时候如果直接拿这些原始数据去计算则会非常缓慢,这对我们实时运行没有好处,我们需要提取出新的特征。(减少数据维度) 我们通过原始数据很多维特征,得到一个新的特征,最后通过这个新的特征来指导做决策。(整理已有的数据特征) 作者:吃果冻不吐果冻皮 链接:https://juejin.cn/post/69986867315
|
机器学习/深度学习 存储 算法
Paper:《CatBoost: unbiased boosting with categorical features》的翻译与解读
Paper:《CatBoost: unbiased boosting with categorical features》的翻译与解读
Paper:《CatBoost: unbiased boosting with categorical features》的翻译与解读
|
机器学习/深度学习 数据挖掘 算法框架/工具
Keras之DNN::基于Keras(sigmoid+binary_crossentropy+predict_classes)利用DNN实现二分类——DIY二分类数据集&预测新数据点
Keras之DNN::基于Keras(sigmoid+binary_crossentropy+predict_classes)利用DNN实现二分类——DIY二分类数据集&预测新数据点
Keras之DNN::基于Keras(sigmoid+binary_crossentropy+predict_classes)利用DNN实现二分类——DIY二分类数据集&预测新数据点
|
机器学习/深度学习 存储 算法
Paper:《CatBoost: unbiased boosting with categorical features》的翻译与解读(二)
Paper:《CatBoost: unbiased boosting with categorical features》的翻译与解读(二)