文本分类是机器学习在自然语言处理中的最常用也是最基础的应用,机器学习相关内容可以直接看我的有关scikit-learn相关教程,本节直接涉及nltk中的机器学习相关内容
转载自网站www.shareditor.com
以及原始链接地址
先来一段前戏
机器学习的过程是训练模型和使用模型的过程,训练就是基于已知数据做统计学习,使用就是用统计学习好的模型来计算未知的数据。
机器学习分为有监督学习和无监督学习,文本分类也分为有监督的分类和无监督的分类。有监督就是训练的样本数据有了确定的判断,基于这些已有的判断来断定新的数据,无监督就是训练的样本数据没有什么判断,完全自发的生成结论。
无论监督学习还是无监督学习,都是通过某种算法来实现,而这种算法可以有多重选择,贝叶斯就是其中一种。在多种算法中如何选择最适合的,这才是机器学习最难的事情,也是最高境界。
nltk中的贝叶斯分类器
贝叶斯是概率论的鼻祖,贝叶斯定理是关于随机事件的条件概率的一则定理,贝叶斯公式是:
P(B|A)=P(A|B)P(B)/P(A);即,已知P(A|B),P(A)和P(B)可以计算出P(B|A)。
贝叶斯分类器就是基于贝叶斯概率理论设计的分类器算法,nltk库中已经实现,具体用法如下:
sys
sys
syssetdefaultencoding
nltk
my_train_set
classifier nltkNaiveBayesClassifiertrainmy_train_set
classifierclassify
classifierclassify
执行后判断特征a和特征b的分类分别是3和2
因为训练集中特征是a的分类是3的最多,所以会归类为3
当然实际中训练样本的数量要多的多,特征要多的多
请尊重原创,转载请注明来源网站www.shareditor.com以及原始链接地址
文档分类
不管是什么分类,最重要的是要知道哪些特征是最能反映这个分类的特点,也就是特征选取。文档分类使用的特征就是最能代表这个分类的词。
因为对文档分类要经过训练和预测两个过程,而特征的提取是这两个过程都需要的,所以,习惯上我们会把特征提取单独抽象出来作为一个公共方法,比如:
nltkcorpus movie_reviewsall_words nltkFreqDistwlower w movie_reviewswords
word_features all_wordskeys
document
word word_features
features word word document_words
features
这是一个简单的特征提取过程,前两行找到movie_reviews语料库中出现词频最高的2000个词作为特征,下面定义的函数就是特征提取函数,每个特征都是形如contains(***)的key,value就是True或False,表示这个词是否在文档中出现
那么我们训练的过程就是:
featuresets document_featuresd c dc documentsclassifier nltkNaiveBayesClassifiertrainfeaturesets
要预测一个新的文档时:
classifierclassifydocument_featuresd
通过
classifiershow_most_informative_features
可以找到最优信息量的特征,这对我们选取特征是非常有帮助的
其他文本分类
文本分类除了文档分类外还有许多其他类型的分类,比如:
词性标注:属于一种文本分类,一般是基于上下文语境的文本分类
句子分割:属于标点符号的分类任务,它的特征一般选取为单独句子标识符的合并链表、数据特征(下一个词是否大写、前一个词是什么、前一个词长度……)
识别对话行为类型:对话行为类型是指问候、问题、回答、断言、说明等
识别文字蕴含:即一个句子是否能得出另外一个句子的结论,这可以认为是真假标签的分类任务。这是一个有挑战的事情
从一句话里提取出十句话的信息,扩充训练样本
按照之前理解的内容,对一句话做处理,最多是切成一个一个的词,再标注上词性,仅此而已,然而事实并非如此,一句话还可以做更多的文章,如下:
什么?还能结构化?
任何语言的每一句话之所以称为“话”,是因为它有一定的句子结构,除了一个个独立的词之外,他们之间还存在着某种关系。如果任何一句话可以由任何词构成,可长可短,那么这是一个非结构化的信息,计算机是很难理解并做计算的,但是如果能够以某种方式把句子转化成结构化的形式,计算机就可以理解了。而如果建立结构化的知识之间的关系图,则所谓的知识图谱 。
实事上,人脑在理解一句话的时候也暗暗地在做着由非结构化到结构化的工作。
比如说:“我下午要和小明在公司讨论一个技术问题”。这是一片非结构化的词语拼成的一句话,但是这里面有很多隐含信息:
1)小明是一个实体
2)参与者有两个:我和小明
3)地点设定是:公司
4)要做的事情是:讨论
5)讨论的内容是:问题
6)这个问题是一个技术问题
7)公司是一个地点
8)讨论是一种行为
9)我和小明有某种关系
10)下午是一个时间
上面这些信息有一些是专门针对这个句子的,有一些是常理性的,对于针对句子的信息有利于理解这句话,对于常理性的信息可以积累下来用来以后理解其他句子。
那么怎么才能把非结构化的句子转成结构化的信息呢?要做的工作除了断句、分词、词性标注之外,还要做的一个关键事情就是分块。
分块
分块就是根据句子中的词和词性,按照某种规则组合在一起形成一个个分块,每个分块代表一个实体。常见的实体包括:组织、人员、地点、日期、时间等
以上面的例子为例,首先我们做名词短语分块(NP-chunking),比如:技术问题。名词短语分块通过词性标记和一些规则就可以识别出来,也可以通过机器学习的方法识别
除了名词短语分块还有很多其他分块:介词短语(PP,比如:以我……)、动词短语(VP,比如:打人)、句子(S,我是人)
分块如何标记和存储呢?
可以采用IOB标记,I(inside,内部)、O(outside,外部)、B(begin, 开始),一个块的开始标记为B,块内的标识符序列标注为I,所有其他标识符标注为O
也可以用树结构来存储分块,用树结构可以解决IOB无法标注的另一类分块,那就是多级分块。多级分块就是一句话可以有多重分块方法,比如:我以我的最高权利惩罚你。这里面“最高权利”、“我的最高权利”、“以我的最高权利”是不同类型分块形成一种多级分块,这是无法通过IOB标记的,但是用树结构可以。这也叫做级联分块。具体树结构举个例子:
小明
追赶
一只
兔子
这是不是让你想到了语法树?
关系抽取
通过上面的分块可以很容易识别出实体,那么关系抽取实际就是找出实体和实体之间的关系,这是自然语言处理一个质的跨越,实体识别让机器认知了一种事物,关系识别让机器掌握了一个真相。
关系抽取的第一个方法就是找到(X, a, Y)这种三元组,其中X和Y都是实体,a是表达关系的字符串,这完全可以通过正则来识别,因为不同语言有这不同的语法规则,所以方法都是不同的,比如中文里的“爱”可以作为这里的a,但是“和”、“因为”等就不能作为这里的a
编程实现
下面介绍部分有关分块的代码,因为中文标注好分块的语料没有找到,所以只能沿用英文语料来说明,但是原理是一样的
conll2000语料中已经有标注好的分块信息,如下:
nltkcorpus conll2000 conll2000chunked_sents
S
PP OverIN
NP aDT cupNN
PP ofIN
NP coffeeNN
NP MrNNP StoneNNP
VP toldVBD
NP hisPRP$ storyNN
我们可以基于这些标注数据做训练,由于这种存储结构比较特殊,所以就不单独基于这种结构实现parser了,只说下跟前面讲的机器学习一样,只要基于这部分数据做训练,然后再用来标注新的语料就行了
这里介绍一下 sklearn 库中的的一个文本分类 demo
以下为笔者自己编辑:
numpy np
sklearnnaive_bayes MultinomialNB BernoulliNB
sklearndatasets fetch_20newsgroups
sklearnfeature_extractiontext TfidfVectorizer
sklearnlinear_model RidgeClassifier
sklearnneighbors KNeighborsClassifier
sklearnsvm SVC
sklearnensemble RandomForestClassifier
sklearnmodel_selection GridSearchCV
sklearn metrics
time time
pprint pprint
matplotlibpyplot plt
matplotlib mpl
clf
clf
alpha_can nplogspace
model GridSearchCVclf param_grid alpha_can cv
m alpha_cansize
clf
modelset_paramsparam_grid alpha_can
m alpha_cansize
clf
neighbors_can nparange
modelset_paramsparam_grid neighbors_can
m neighbors_cansize
clf
C_can nplogspace
gamma_can nplogspace
modelset_paramsparam_gridC_can gamma_can
m C_cansize gamma_cansize
clf
max_depth_can nparange
modelset_paramsparam_grid max_depth_can
m max_depth_cansize
t_start time
modelfitx_train y_train
t_end time
t_train t_end t_start m
t_end t_start m t_train
modelbest_params_
t_start time
y_hat modelpredictx_test
t_end time
t_test t_end t_start
t_test
acc metricsaccuracy_scorey_test y_hat
acc
name clfsplit
index namefind
index
name nameindex
name
name
t_train t_test acc name
__name__
t_start time
remove
categories
data_train fetch_20newsgroupssubset categoriescategories shuffle random_state removeremove
data_test fetch_20newsgroupssubset categoriescategories shuffle random_state removeremove
t_end time
t_end t_start
data_train
data_traindata
data_testdata
categories
categories data_traintarget_names
pprintcategories
y_train data_traintarget
y_test data_testtarget
i nparange
i categoriesy_traini
data_traindatai
vectorizer TfidfVectorizer stop_words max_df sublinear_tf
x_train vectorizerfit_transformdata_traindata
x_test vectorizertransformdata_testdata
x_trainshape
pprintvectorizerget_stop_words
feature_names npasarrayvectorizerget_feature_names
clfs MultinomialNB
BernoulliNB
KNeighborsClassifier
RidgeClassifier
RandomForestClassifiern_estimators
SVC
result
clf clfs
a test_clfclf
resultappenda
result nparrayresult
time_train time_test err names resultT
time_train time_trainastypenp
time_test time_testastypenp
err errastypenp
x nparangetime_train
mplrcParams
mplrcParams
pltfigurefigsize facecolor
ax pltaxes
b1 axbarx err width color
ax_t axtwinx
b2 ax_tbarx time_train width color
b3 ax_tbarx time_test width color
pltxticksx names
pltlegendb1 b2 b3 loc shadow
plttitle fontsize
pltxlabel
pltgrid
plttight_layout
pltshow
还没有评论,来说两句吧...