• 本文目录

    • 一、Fasttext算法综述
    • 二、原理介绍及优化策略
    • 三、Fasttext算法实战(注:以下代码仅在Linux系统下使用!)
    • 四、参考资料

本文目录(仅做浏览用,暂时不支持页面内跳转)

一、Fasttext算法综述

  • Fasttext是Facebook AI Research2016年推出的文本分类和词训练工具,其源码已经托管在Github上。Fasttext最大的特点是模型简单,只有一层的隐层以及输出层,因此训练速度非常快,在普通的CPU上可以实现分钟级别的训练,比深度模型的训练要快几个数量级。同时,在多个标准的测试数据集上,Fasttext在文本分类的准确率上,和现有的一些深度学习的方法效果相当或接近。

二、原理介绍及优化策略

  • 1.Fasttext算法的主要功能有两个:

    • (1). 训练词向量:词向量的训练相对与word2vec来说增加了subwords特性。subwords其实就是一个词的字符级的n-gram。例如单词"hello",长度至少为3的char-level的ngram有”hel”,”ell”,”llo”,”hell”,”ello”以及本身”hello”。每个n-gram都可以用一个dense的向量zg表示,于是整个单词”hello”就可以表示表示为:

      具体细节可以参考论文Enriching Word Vectors with Subword Information那么把每个word,拆成若干个char-level的ngram表示有什么好处呢?答案是:丰富了词表示的层次。例如:”english-born”和”china-born”,从单词层面上看,是两个不同的单词,但是如果用char-level的n-gram来表示,都有相同的后缀”born”。因此这种表示方法可以学习到当两个词有相同的词缀时,其语义也具有一定的相似性。这种方法对英语等西方语言来说可能是奏效的。因为英语中很多相同前缀和后缀的单词,语义上确实有所相近。但对于中文来说,这种方法可能会有些问题。比如说,”原来”和”原则”,虽有相同前缀,但意义相去甚远。可能对中文来说,按照偏旁部首等字形的方式拆解可能会更有意义一些。
    • (2). 文本分类:Fasttext的另一个功能是做文本分类。主要的原理在论文Bag of Tricks for Efficient Text Classification中有所阐述。其模型结构简单来说,就是一层word embedding的隐层+输出层。结构如下图所示:


      图1是Fasttext的网络结构,其中W1到Wn表示document中每个词的word embedding表示。文章则可以用所有词的embedding累加后的均值表示,即:

      最后从隐层再经过一次的非线性变换得到输出层的label。对比word2vec中的图2中的CBOW模型(continuous bag of word),可以发现两个模型之前非常的相似。不同之处在于,fasttext模型最后预测的是文章的类别label,而CBOW模型预测的是窗口中间的词w(t),Fasttext是有监督的学习,CBOW是无监督的学习。另外,CBOW模型中输入层只包括当前窗口内除中心词外的所有上下词汇,而fasttext模型中输入层是文章中的所有词。
  • 2.网络结构介绍及模型的优化trick
    • 2.1模型结构介绍

      • 和word2vec类似,fasttext本质上也可以看成是一个浅层的神经网络,因此其前向传播过程可描述如下:

        其中,z是最后输出层的输入向量,Wo表示从隐藏层到输出层的权重
      • 由于模型的最后输出是要预测的文本属于某个类别的概率,因此很自然的使用标准的softmax层,见下图:

        标准的softmax层用于多分类任务中,它将多个神经元的输出映射到(0,1)之间,可以当作概率来理解,从而进行多分类。在最后选取输出节点时,选取概率最大的节点作为最终的预测值。定义的交叉熵损失函数CE(y_target,y_predict)如下:
    • 2.2 模型优化的几个trick
      • 2.2.1当类别数较少时,直接套用softmax层并没有效率问题,但是当类别很多时,softmax层的计算就比较费时。为了加快训练过程,Fasttext同样也采用了和word2vec类似的方法。一种方法是使用hierarchical softmax,当类别数为K,word embedding的维度大小为d时,计算复杂度可以从O(Kd)降到O(dlog(K))。

        因为在标准的softmax回归中,要计算y=j时的softmax概率P(y=i),需要对所有的K个概率做归一化,这在类别很大是会很耗时,于是分层softmax诞生了。分层softmax的基本思想:使用树的层级结构替代扁平化的标准softmax,使得在计算P(y=j)时,只需要计算一路路径上的所有节点的概率值即可,不需在意其他的节点。树的结构是根据类别的频数构造的霍夫曼树。K个不同的类别组成所有的叶子节点,K-1个内部节点作为内部参数,从根节点到某个叶子节点和边构成一条路径,路径的长度表示为L(yj)。于是,P(yj)可以写成下式:

        其中:

        • sigmoid():表示sigmoid函数
        • LC(n):表示n节点的左孩子
        • [[x]]是一个特殊的函数,定义如下:
        • theta(yj,l):表示中间节点n(yj,l)的参数,X是softmax层的输入
          上图中,高亮的节点和边是从根节点到y2的路径,路径长度是L(y2)=4,所以P(y2)可表示为:

          于是,从根节点到叶子节点y2,实际上作出3次的二分类的逻辑回归,通过分层的softmax,计算复杂度从O(K)降到O(log(K))。
      • 2.2.2 另一种方法是采用negative sampling,即每次从除当前label(正样本)外的其他label(负样本)中选择几个作为负样本,作为出现负样本的概率加到损失函数中,用公式可表达为:

        其中,hi是第i个样本的隐藏层神经元数量,uj是Wo中第j行向量
      • 2.2.3 n-gram特征解决Fasttext模型丢失词汇顺序的问题,因为隐层是通过简单的求和取平均得到的。为了弥补这个不足,Fasttext增加了N-gram的特征。具体做法:把N-gram当成一个词,也用embedding向量来表示,在计算隐层时,把N-gram的embedding向量也加进去求和取平均。举个例子来说,假设某篇文章只有3个词,W1,W2,W3,N-gram的N=2即是bigram,w1、w2、w3以及w12、w23分别表示词W1、W2、W3和bigram W1-W2,W2-W3的embedding向量,那么文章的隐层可表示为:

        通过反向传播算法,就可以同时学到词的Embeding和n-gram的Embedding,具体的实现上,由于n-gram的量远比word大的多,完全存下所有的n-gram也不现实。Fasttext采用了Hash桶的方式,把所有的n-gram都哈希到buckets个桶中,哈希到同一个桶的所有n-gram共享一个embedding vector。如下图所示:

        图中Win是Embedding矩阵,每行代表一个word或N-gram的词向量,其中前V行是word embeddings,后Buckets行是n-grams embeddings。每个n-gram经哈希函数哈希到0-bucket-1的位置,得到对应的embedding向量。用哈希的方式既能保证查找时O(1)的效率,又可能把内存消耗控制在O(bucket×dim)范围内。不过这种方法潜在的问题是存在哈希冲突,不同的n-gram可能会共享同一个embedding。如果桶大小取的足够大,这种影响会很小。
      • 2.2.4 对计算复杂度比较高的运算,Fasttext都采用了预计算的方法,先计算好值,使用的时候再查表,这是典型的空间或时间的优化思路。比如sigmoid函数的计算,源代码如下:
      • 2.2.5 在Negative Sampling中,Fasttext也采用了和word2vec类似的方法,即按照每个词的词频进行随机负采样,词频越大的词,被采样的概率越大。每个词被采样的概率并不是简单的按照词频在总量的占比,而是对词频先取根号,再算占比,公式如下:

        其中,fw表示单词w的词频。取根号的目的是降低高频词汇的采样频率,同时增加低频词的采样频率。

三、Fasttext算法实战(注:以下代码仅在Linux系统下使用!)

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Date    : 2019-01-01 21:03:59
# @Author  : cdl (1217096231@qq.com)
# @Link    : https://github.com/cdlwhm1217096231
# @Version : $Id$import fasttext
import jieba
import os
import logginglogging.basicConfig(format='%(asctime)s: %(levelname)s: %(message)s', level=logging.INFO)"""
第1步:获取分类文本,文本直接使用清华大学新闻文本,输出格式是:样本+样本标签
所使用的训练集和测试集已经分词好了,每个样本后会用Tab键隔开,打上样本标签,例如__label__sports
"""# 空缺"""
第2步:利用fasttext进行分类,使用fasttext包
"""# 训练模型
classifier = fasttext.supervised("./dataset/news_fasttext_train.txt", "news_fasttext.model", label_prefix="__label__")
# 训练好的模型
# classifier = fasttext.load_model('new_fasttext.model.bin', label_prefix="__label__")# 测试模型
result = classifier.test("./dataset/news_fasttext_test.txt")
print("准确率:", result.precision)
print("召回率:", result.recall)# fasttext只是对整个文本提供precision和recall,要统计不同的分类结果,需要自己实现classifier = fasttext.load_model('news_fasttext.model.bin', label_prefix='__label__')
labels_right = []
texts = []
with open("./dataset/news_fasttext_test.txt") as f:for line in f:line = line.strip()labels_right.append(line.split('\t')[1].replace("__label__", ""))texts.append(line.split('\t')[0])labels_predict = [e[0] for e in classifier.predict(texts)]  # 预测标签值
text_labels = list(set(labels_right))  # 实际标签值
text_predict_labels = list(set(labels_predict))  # 去重后,预测标签值# print("预测标签值:", text_predict_labels)
# print("真实标签值:", text_labels)A = dict.fromkeys(text_labels, 0)  # 预测正确的各个类的数目,真阳性TP
B = dict.fromkeys(text_labels, 0)  # 真实测试数据集中各个类的数目
C = dict.fromkeys(text_predict_labels, 0)  # 预测结果中各个类的数目,所有的预测结果
for i in range(0, len(labels_right)):B[labels_right[i]] += 1C[labels_predict[i]] += 1if labels_right[i] == labels_predict[i]:  # 判断是否是真阳性TP样本A[labels_right[i]] += 1print("真阳性样本TP的类别数目A:", A)
print("测试数据集中各个类别的数目B:", B)
print("预测结果中各个类别的数目C:", C)
# 计算准确率,召回率,F值
for key in B:try:r = float(A[key]) / float(B[key])   # 召回率p = float(A[key]) / float(C[key])  # 准确率f = p * r * 2 / (p + r)   # f1值print("%s:\t p:%f\t r:%f\t f:%f" % (key, p, r, f))except:print("错误:", key, "正确:", A.get(key, 0), "real:",B.get(key, 0), "预测:", C.get(key, 0))

四、参考资料

1.Bag of Tricks for Efficient Text Classification
2.Enriching Word Vectors with Subword Information
3.玩转Fasttext
4.fastText原理及实践
5.手打例子一步一步带你看懂softmax函数以及相关求导过程
6.使用fastText对文本进行分类
7.训练集数据下载链接
8.测试集数据下载链接

Bag of Tricks for Efficient Text Classification论文阅读及实战相关推荐

  1. Bag of Tricks for Efficient Text Classification(Fasttext)

    Fasttext历史意义: 1.提出一种新的文本分类方法-Fasttext,能够快速进行文本分类,效果较好 2.提出一种新的使用子词的词向量训练方法,能够在一定程度上解决oov问题 3.将Fastte ...

  2. 【文本分类】ACT: an Attentive Convolutional Transformer for Efficient Text Classification

    ·阅读摘要:   本文在Transformer模型的基础上,提出改进方案,把Transformer里面的自注意力机制,改成CNN. ·参考文献:   [1] ACT: an Attentive Con ...

  3. EAST: An Efficient and Accurate Scene Text Detector 论文阅读

    EAST: An Efficient and Accurate Scene Text Detector 论文阅读 Reference 正文 摘要 引言 相关工作 方法 算法 网络设计 标签生成 损失函数 ...

  4. SPIN: Structure-Preserving Inner Offset Network for Scene Text Recognition —— 论文阅读笔记

    SPIN:用于场景文本识别的保留结构的内部偏移网络 Paper : 论文地址 本文提出的方法主要解决色彩失真的图片.如下图中的(c)和(d) SPIN(Structure-Preserving Inn ...

  5. GST: Grouped Spatial-Temporal Aggregation for Efficient Action Recognition 论文阅读

    Grouped Spatial-Temporal Aggregation for Efficient Action Recognition 要解决的问题:作者对比了Kinetic和Diving48这两 ...

  6. Knowledge-based Collaborative Deep Learning for Benign-Malignant Lung Nodule Classification论文阅读

    作者信息: Yutong Xie, Yong Xia, Member, IEEE, Jianpeng Zhang, Yang Song, Member, IEEE, Dagan Feng, Fel l ...

  7. 3.Spatially Attentive Output Layer for Image Classification 论文阅读

    第一次写阅读论文的博客,因公式太多,在csdn上实在敲不下去了.索性直接把word版本上传了上去,仅供大家参考!(阅读论文的时候,为了加深对内容的理解,把公式都给敲了上去,如有错误,请见谅.语言方面, ...

  8. CRAFT: Character Region Awareness for Text Detection ---- 论文阅读笔记

    基于字符区域感知的文本检测 论文地址:https://arxiv.org/abs/1904.01941 论文翻译:https://blog.csdn.net/m0_38007695/article/d ...

  9. MSR: Multi-Scale Shape Regression for Scene Text Detection 论文阅读笔记

    MSR: Multi-Scale Shape Regression for Scene Text Detection 1. 基本信息 文章来源:arxiv(录用期刊或会议未知) SAST链接 上传时间 ...

最新文章

  1. 单片机预备知识(电平、进制转换、字节、数据类型)
  2. C++ 与Qt开发人机象棋(第一部分)
  3. vue 实现数据滚动显示_vue实现动态添加数据滚动条自动滚动到底部的示例代码...
  4. 新建MVC项目与发布
  5. js 指定年月获取最后天
  6. 广播接收者android,电话拦截广播,电话接收者demo
  7. 读caffe源码:gflags的使用
  8. mysql数据库插入数据错误Error Code: 1118 - Row size too large ( 8126)
  9. word操作技巧总结--图片无法显示复制、空格、字体无法修改等
  10. 村田 - ESD 保护装置的基础知识
  11. can例程 ecu_ECU程序及CAN总线实现
  12. 杂文 | 金沙江创投朱啸虎谈微信小程序
  13. 什么是抽象类,接口?他们的区别?(详解)
  14. 基于Autoware制作高精地图(一)
  15. usb接口供电不足_win7笔记本USB接口不够用的解决教程
  16. 区块链溯源是什么?一文带您读懂!
  17. C语言-qsort函数详解及使用例
  18. 《Serverless 与容器决战在即?有了弹性伸缩就不一样了》
  19. 感悟生活,我们的创造力去哪了?谈谈我们的教育
  20. 【人工智能】如何看待人工智能技术的变革与未来? 分10个方面来详细展开谈谈,不少于5000字。

热门文章

  1. Exchange如何将邮件转发给外部邮件地址
  2. 微软:超过96%的企业用户正在测试Win10
  3. Java Web 程序员的发展趋势分析
  4. matlab中find函数的使用说明
  5. linux高级数据存储
  6. 风暴数码论坛教程--加入ROOT等文件及方法
  7. MySQL基础篇:数据类型
  8. 京东热点key探测系统发布,单机 QPS 提升至 37 万
  9. 看完这篇,code review 谁敢喷你代码写的烂?怼回去!
  10. 面对复杂业务架构,阿里架构师是如何做的?(第一期)