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

transformer-PositionalEncoding (对数空间计算实现)

PositionalEncoding (对数空间计算实现)

  • 参考论文:https://arxiv.org/pdf/1706.03762

    https://arxiv.org/pdf/1706.03762

    image-20250422213507984

    位置编码的正常实现链接如下

    https://blog.csdn.net/hbkybkzw/article/details/147431820

    这次说的是位置编码的另一种实现方式,在计算分母的幂次时使用对数变换技巧,在数值上更稳定,两者只是在计算上不同,实际是等价的


数学公式

  • 原公式

    P E ( p o s , 2 i ) = sin ⁡ ( p o s 10000 2 i d m o d e l ) P E ( p o s , 2 i + 1 ) = cos ⁡ ( p o s 10000 2 i d m o d e l ) PE_{(pos,2i)} = \sin ( \frac{pos}{10000^{ \frac{2i}{d_{model}} } } ) \\ \quad \\ PE_{(pos,2i+1)} = \cos ( \frac{pos}{10000^{ \frac{2i}{d_{model}} } } ) \\ PE(pos,2i)=sin(10000dmodel2ipos)PE(pos,2i+1)=cos(10000dmodel2ipos)

    其中, p o s pos pos 表示位置, i i i 是维度索引, d m o d e l d_{model} dmodel 是模型的维度 (即embedding的维度)。

  • 分母的变换

    已知
    x = e log ⁡ ( x ) x = e^{\log_(x)} x=elog(x)

    $$
    \begin{aligned}
    \frac{1}{10000^{ \frac{2i}{d_{model}}}} &= 10000^{-\frac{2i}{d_{model} }} \
    &=e^{\log 10000^{-\frac{2i}{d_{model} }} } \
    &=e^{{-\frac{2i}{d_{model} }} \log 10000} \
    &=e^{-2i \log{10000} / d_{model} } \

    \end{aligned}
    $$

  • 所以原来的实现代码为

    item = 1 / 10000 ** (torch.arange(0, d_model, 2) / d_model)
    

    更改为对数计算后是

    div_item = torch.exp(torch.arange(0, d_model, 2) * -(math.log(10000.0)) / d_model)
    

代码实现 (对数空间计算)

  • 根据上述公式,PositionalEncoding的一种实现方式如下,其中div_term的计算在对数空间进行,以提高数值稳定性:

    import torch
    from torch import nn
    import mathclass PositionalEncodingExponent(nn.Module):"Implement the PE function."def __init__(self, d_model, max_seq_len=512):super(PositionalEncodingExponent, self).__init__()# shape of position : [max_seq_len, 1]position = torch.arange(0, max_seq_len).unsqueeze(1)# Compute the positional encodings once in log space.div_item = torch.exp(torch.arange(0, d_model, 2) * -(math.log(10000.0)) / d_model)tmp_pos = position * div_itempe = torch.zeros(max_seq_len, d_model)pe[:, 0::2] = torch.sin(tmp_pos)pe[:, 1::2] = torch.cos(tmp_pos)pe = pe.unsqueeze(0)self.register_buffer("pe", pe,persistent=False)def forward(self, x):batch,seq_len,d_model = x.shape # 注意,这里的x已经经过embeddingpe = self.pereturn x + pe[:, :seq_len, :]

使用示例

  • 测试代码

    # 假设我们有一个大小为 (batch_size=32, seq_len=20, d_model=512) 的输入
    batch_size = 32
    seq_len = 20
    d_model = 512# 创建位置编码的实例
    pos_encoding_layer = PositionalEncodingExponent(d_model=d_model)# 生成随机输入数据
    input_data = torch.randn(batch_size, seq_len, d_model)# 获取带有位置编码的数据
    output_data = pos_encoding_layer(input_data)print(output_data.shape)  # 输出应为 (32, 20, 512)
    

    此示例创建了一个PositionalEncoding类的实例,并将其应用于一个随机生成的输入张量,模拟了在Transformer模型中将位置信息添加到词嵌入的过程。输出张量的形状与输入张量保持一致。

http://www.xdnf.cn/news/9646.html

相关文章:

  • 行业案例 | OPPO借助Azure AI Speech国际服务实现音频文件智能转录
  • 基于MATLAB的二维圆形随机骨料生成程序
  • APL Photonics封面成果:KAUST用五边形激光腔刷新物理随机数生成极限——800Gb/s!
  • Selenium 测试框架 - JavaScript
  • Xamarin入门笔记(Xamarin已经被MAUI取代)
  • 利益相关者意见分歧,如何决策
  • 在线临床指标分类信息表转甜甜圈矩阵图
  • 将git最后一次提交把涉及到的文件按原来目录结构提取出来
  • LLM中的Loss与Logits详解
  • 【leetcode】206. 反转链表
  • Linux Shellcode开发(Stager Reverse Shell)
  • 简述MySQL优化锁方面你有什么建议?
  • 彰显国产力量|暴雨亮相2025 C3安全峰会
  • Guava限频器RateLimiter的使用示例
  • STM32学习第一课--工程建立(云端备份与自我复盘)
  • ROS2学习(16)------ URDF 机器人建模方法
  • 操作系统 | 第一章:操作系统引论思维导图
  • 解决ssh: connect to host IP port 22: Connection timed out报错(scp传文件指定端口)
  • Java—多线程
  • 如何使用 poetry 创建虚拟环境,VSCode 如何激活使用 Poetry 虚拟环境(VSCode如何配置 Poetry 虚拟环境)
  • MVCC原理解析
  • js 手写promise
  • 专栏更新通知
  • Python 科学计算有哪些提高运算速度的技巧
  • 力扣——1.两数之和
  • 【论文阅读】User Diverse Preference Modeling by Multimodal Attentive Metric Learning
  • 【笔记】修改abu量化本地部署数据文件夹目录
  • OpenCV CUDA模块直方图计算------用于在 GPU 上执行对比度受限的自适应直方图均衡类cv::cuda::CLAHE
  • Python 的 `next()`函数
  • 数字化回归本质:第一性原理驱动的制造业转型与AI+云PLM系统实践