当前位置: 首页 > article >正文

关于 Embedding 的个人粗略见解

首先举一个简单的例子:我爱吃饭。

如何将 “我爱吃饭” 这句话转化为可供神经网络输入的数值向量呢?

最传统的方法就是通过 one-hot 编码,用一维向量分别表示 “我”,“爱”,“吃”,“饭” 这四个字(token),它们分别被编码为:

  • 我:[ 1 0 0 0 ]
  • 爱:[ 0 1 0 0 ]
  • 吃:[ 0 0 1 0 ]
  • 饭:[ 0 0 0 1 ]

最终 “我爱吃饭” 这句话就被编码为一个特征矩阵,且这个矩阵唯一表示这句话。

但是 one-hot 编码存在较大的局限性:

  1. 每个 token 编码得到的维度大小必须与所有 token 的个数保持一致,有 n 个 token,向量维度就为 n,导致 token 数量较多时,出现维度爆炸模型无法正常训练。
  2. 由于特征矩阵中的数值大部分都为 0,最终得到的是稀疏向量,导致模型很难学习到对于结果预测真正有效的信息。

为了解决上述问题,Embedding(嵌入层)随之而来。Embedding,在某种程度上可以理解为,就是用来降维的,而降维的原理就是矩阵乘法。

1 降维

假设存在一个维度为 4 x 2 的系数矩阵:

  • [ w1 w2 ]
  • [ w3 w4 ]
  • [ w5 w6 ]
  • [ w7 w8 ]

“我爱吃饭” 对应 onehot 编码得到的稀疏特征矩阵(4 x 4)经过 Embedding 层后得到一个维度为 4 x 2 的稠密矩阵:

  • [ y1 y2 ]
  • [ y3 y4 ]
  • [ y5 y6 ]
  • [ y7 y8 ]

也就是说,经过 Embedding 层,一个维度为 4 x 4 的稀疏矩阵转化为了一个维度为 4 x 2 的稠密矩阵,做到了降维的同时丰富了特征。

2 特征扩充

目前大多数 token 的编码方法不采用 one-hot,而是采用字典(dictionary)或语料库(corpus)为每个token 分配一个唯一索引。例如存在一个字典/语料库:

0
1
2
3
4
5
......

那么 “我爱吃饭” 就可以表示为一维向量 [ 1 2 3 5 ],而 “他爱吃饭”表示为 [ 0 2 3 5 ],“你爱吃饭” 表示为 [ 4 2 3 5 ],可以明显地发现三者的特征向量过于相似了(即使它们的语义不同)。在这种情况下,Embedding 层可用于升维,将某些特征进行放大,或将一些相似特征区分开来。

同样假设存在一个维度为 4 x 8 的系数矩阵:

  • [ w1 w2 w3 w4 w5 w6 w7 w8 ]
  • [ .... .... .... .... .... .... .... .... .... ]
  • [ .... .... .... .... .... .... .... .... .... ]
  • [ .... .... .... .... .... .... .... .... .... ]

“我爱吃饭“ 通过 Embedding 层后得到新的维度为 1 x 8 的特征矩阵:

[ y1 y2 y3 y4 y5 y6 y7 y8 ]

最终,4 个特征转化为了 8 个特征,扩大了特征之间的相似性。

3 公式

众所周知,基础神经网络模型可以大致表示为:

y = w * x + b

w 表示参数矩阵;b 表示偏置(bias)或 y 轴上的截距。根据激活函数的不同输出 y 大致上分为两种:

  • 输入 x --> 对应输出 ( 0.9 ),通过设定的阈值得到标签 1;而对应输出 ( 0.4 ),通过设定的阈值得到标签 0,这种情况适用于二分类。
  • 输入 x --> 对应输出 ( 0.1, 0.4, 0.9 ),选择最大值所对应的索引作为标签值输出,如 0.9 对应索引 2,这种情况适用于二分类及多分类。

同理,在某种程度上可以将 Embedding 过程可以理解为下列公式:

Y = W * X

W 表示系数矩阵;X 表示初始特征向量/矩阵;Y 则表示经过 Embedding 后得到的稠密矩阵。

1.4 预训练模型和微调

目前热门预训练模型如 transformer,bert,gpt 等,之所以被称为预训练模型,是因为它们事先从大规模数据集中训练好了系数矩阵 W,我们可以直接在自己的任务中调用该模型,以更高的效率得到更为精确的特征向量矩阵,而无需自己从头开始训练得到系数矩阵 W。

同样,当我们的任务所采用的数据集与预训练模型不一致时,将其在自己的数据集上进行微调,从而得到更符合自己任务的系数矩阵 W,为下游分类任务做铺垫。


http://www.kler.cn/a/302189.html

相关文章:

  • java Redis 操作工具类封装(备忘)
  • LeetCode:1387. 将整数按权重排序(记忆化搜索 Java)
  • Vue.js 响应接口
  • unity Toggle制作滑动开关
  • 维克日记:私密写作新选择,轻松记录生活点滴
  • 如何利用Python爬虫获得1688按关键字搜索商品
  • cross-plateform 跨平台应用程序-05-Flutter 介绍
  • 【2024 版】最新 kali linux 入门及常用简单工具介绍(非常详细)
  • Unet改进30:添加CAA(2024最新改进方法)|上下文锚定注意模块来捕获远程上下文信息。
  • UE5 性能分析 UnrealInsights
  • MATLAB下载详细教程及下载链接
  • 如何取消密码?打印加密的PDF文件?
  • [论文笔记] ShortGPT Qwen2-0.5B-instruct Qwen2-1.5B-instruct 大模型剪枝
  • 总结拓展九:SAP数据迁移(1)
  • mfc140u.dll错误是什么情况?如何将mfc140u.dll丢失的解决方法详细分析
  • 攻防世界 CTF Pwn(一)
  • Codeforces practice /C++ 2024/9/11 - 2024/9/12
  • HTML + js 生成一个线路走向图,可以标记总共有多少站,用户到达第几站了
  • 惩罚矩阵?动态规划是如何爱上矩阵的
  • MyBatis 源码解析:OGNL 表达式解析与使用
  • 银行业务架构指导应用架构规划及设计方法
  • Redis单机、集群、哨兵、主从架构详解
  • 【专题】2024跨境出海供应链洞察-更先进供应链报告合集PDF分享(附原数据表)
  • SpringBoot登录退出|苍穹外卖登录退出分析
  • 软硬链接与动静态库概览
  • 【Python机器学习】循环神经网络(RNN)——循环网络的记忆功能