理想汽车智驾方案介绍专题 3 MoE+Sparse Attention 高效结构解析

一、前言

【理想汽车智驾方案介绍专题 -1】端到端+VLM 方案介绍

【理想汽车智驾方案介绍专题 -2】MindVLA 方案详解

在上述两篇系列帖子中,笔者已对理想汽车 VLM 和 VLA 方案的框架进行了全面介绍,但对于其中的前沿技术仅做了初步探讨,未进行更深入的剖析。因此,笔者计划继续以系列文章的形式,介绍其中涉及的相关前沿技术。

首先,将介绍 MindVLA 中采用的“MoE + Sparse Attention”高效结构。

二、MoE + Sparse Attention 高效结构

稀疏注意力(Sparse Attention)与混合专家架构(MoE)是提升大模型效率与性能的核心技术。MindGPT 针对大语言模型(LLM)进行了重新设计与预训练,使其具备了 3D 空间理解和 3D 推理能力,不过这在一定程度上增加了大语言模型(LLM)的参数量。即便采用英伟达(NV)大力宣传的 Thor - U 智驾芯片,在端侧部署时仍有可能会出现推理效率低下的问题。 所以模型采用了 MOE 架构+SparseAttention,实现模型容量扩容的同时不会大幅度增加推理负担。

img

由上图可以看到,MindGPT 使用混合专家(MoE)架构(有 E1-E8 个专家),由 Router 动态选择激活部分专家(而非全部),只在需要时调用相关子模型。稀疏注意力(Sparse Attention)则限制注意力机制的复杂度,只关注关键输入部分(如相关物体或动作),而不是全局计算。在这张图中,它的实现过程是:

每一层的 token 并不全互相注意,而是:

  • 利用 Router 分配 token 给不同的 expert
  • 每个 expert 内部只在局部或关键 token 上建立注意力连接

这种结构既节省计算,又保持了输入的局部结构性,尤其适合 3D 场景中的空间约束。

2.1 Sparse Attention

参考论文 Generating Long Sequences with Sparse Transformers

传统 transformer 的全连接注意力复杂度为O(n2)O(n^2)O(n2),对于高维空间场景(例如 3D Token 很多)会显著拖慢速度、增加计算。

稀疏注意力的核心目标是:

  • 减少 token-to-token 的注意力连接(只对一部分 token 建立 attention)
  • 降低计算复杂度,同时保持关键 token 的交互质量

那么它是如何实现目标的呢?下面将结合Sparse Transformer代码进行介绍。

Sparse Transformer 是由OpenAI提出的稀疏注意力的最早实现之一,其核心思想是用 规则稀疏模式(Regular Sparse Patterns) 替代标准全连接注意力(full self-attention)。在保持表示能力的同时,将注意力复杂度从

O(n2)O(n^2)O(n2)降低为O(nn)O(n\sqrt n)Onn.

2.1.1 Sparse Attention 图结构解析

img

Strided attention(跳跃连接)

每个 token 关注步长为 s 的若干 token,例如:

位置:      0   1   2   3   4   5   6   7   8
strided:   ↑       ↑       ↑       ↑

token 8 会关注 0, 2, 4, 6 这些步长为 2 的 token。

Local attention(局部窗口)

每个 token 也关注自己附近的窗口内 token,比如前后 2 个:

位置:       5
局部窗口:   3   4   5   6   7
组合结构

将两者合并后,注意力图是 局部窗口 + 跳跃连接,形成稀疏但有覆盖力的结构:

Token 位置:         8
局部连接:         6 7 8
跳跃连接:     0 2 4

这种结构可以保证每个 token 都能快速传播到远端(通过跳跃),并同时保留局部建模能力。

2.1.2 代码实现解析

由于 OpenAI Sparse Transformer 没开源,这里参考了其思想的一个流行实现:[OpenNMT-py 或 custom PyTorch 实现],也可参考 Reformer 等模型实现方式。

稀疏注意力 mask 构造(关键)
def build_sparse_attention_mask(seq_len, block_size=64, num_local_blocks=1, stride=2):"""构造稀疏注意力 mask:局部 + 跳跃"""mask = torch.zeros(seq_len, seq_len, dtype=torch.bool)for i in range(seq_len):# 添加局部窗口(例如前后1个block)for j in range(-num_local_blocks, num_local_blocks + 1):idx = i + j * block_sizeif 0 <= idx < seq_len:mask[i, idx] = True# 添加跳跃连接(stride)for j in range(0, seq_len, stride):mask[i, j] = Truereturn mask

这个 mask 会用于注意力权重:

attn_scores = torch.matmul(query, key.transpose(-2, -1))  # [B, H, N, N]
attn_scores[~mask] = -inf  # 掩蔽非连接位置
attn_probs = softmax(attn_scores)
应用在 Attention 模块

核心 attention 模块不变,只是加了 mask:

def sparse_attention(query, key, value, mask):attn_scores = torch.matmul(query, key.transpose(-2, -1))attn_scores = attn_scores.masked_fill(~mask, float('-inf'))attn_probs = torch.softmax(attn_scores, dim=-1)return torch.matmul(attn_probs, value)

这样就可以在不修改 Transformer 主体结构的前提下使用稀疏连接。

以下是一个 9×9 attention matrix 的稀疏连接可视化(● 表示有连接):

Token ID →0 1 2 3 4 5 6 7 8┌──────────────────
0 │●       ●       ●
1 │  ●     ●     ●
2 │    ●   ●   ●
3 │      ● ● ●
4 │      ● ● ●
5 │      ● ● ●
6 │    ●   ●   ●
7 │  ●     ●     ●
8 │●       ●       ●

中间对角线为 **局部 attention,**分布的条纹为 跳跃 attention。

2.1.3 复杂度分析

标准全连接 Self-Attention 的公式是:

img

QKTQK^TQKT:产生 n×n 的权重矩阵 → 计算复杂度是:O(n2d)O(n^2 d)O(n2d);

Softmax ()V :O(n2d)O(n^2 d)O(n2d);

整体复杂度为:O(n2d)O(n^2 d)O(n2d),这意味着当序列变长时(如 n=8192),计算量和内存都会剧增。

Sparse Transformer 通过限制每个 token 只关注O(n)O(\sqrt{n})O(n)个位置,从而稀疏 attention 矩阵。

每个 token 的 attention 链接数为k=O(n)k=O(\sqrt{n})k=O(n)**,**所有 token 的总链接数就是n⋅k=n⋅nn⋅k=n⋅\sqrt{n}nk=nn

由于只需要对是n⋅nn⋅\sqrt{n}nn 个位置计算 QKᵀ dot product,而不是n2n^2n2 ,每个位置依然是**O(d)的向量操作,**所以 Sparse Transformer 的复杂度是是O(n⋅n)O(n⋅\sqrt{n})O(nn)

2.2 MoE

MoE(专家混合体)是神经网络的一种架构模式,该模式将一个层或操作(例如线性层、多层感知机或注意力投影)的计算拆分为多个“专家”子网络。这些子网络各自独立地进行计算,其计算结果会被整合,以生成 MoE 层的最终输出。MoE 架构可分为密集型和稀疏型,前者意味着在处理每个输入时都会启用所有专家,后者则表示每个输入仅使用部分专家。因此,MoE 架构具备以下优势:

  • 提升计算效率
  • 在不显著增加推理成本的前提下,扩大模型容量(参数量)

这些优势与大模型的应用难题完美匹配,故而在该领域得到了较为广泛的应用。

2.2.1 MoE 结构解析

本节首先描述 MoE 的核心组件,然后以 DeepSpeed-MoE 源代码为例进行详细解析。

以 PyTorch 为例,MoE 的核心组成部分通常包括以下几个模块:

1.Gate 模块(路由器)

负责为每个输入样本选择合适的专家(通常是 top-k 策略):

# 伪代码
scores = gate(x)  # (batch_size, num_experts)
top_k_scores, top_k_indices = torch.topk(scores, k=2)
  • scores 通常是通过一个线性层获得,表示输入样本对各个专家的偏好程度。
  • 路由器可能带有噪声或正则(如 Switch Transformer 中的 noisy gating)。
2.Experts 模块(多个子网络)

每个专家是一个独立的神经网络(比如一个 MLP):

class Expert(nn.Module):def __init__(self, hidden_dim):self.ff = nn.Sequential(nn.Linear(hidden_dim, 4*hidden_dim),nn.ReLU(),nn.Linear(4*hidden_dim, hidden_dim))

通常通过参数共享或并行执行多个专家。

3.Dispatcher(稀疏调度器)

根据 Gate 的输出,将输入路由给选中的专家,并收集输出:

 for i in range(num_experts):expert_input = input[mask[:, i]]expert_output = experts[i](expert_input)output[mask[:, i]] = expert_output * gate_scores[:, i]

这一步骤通常要做优化,否则容易成为性能瓶颈。

2.2.2 DeepSpeed-MoE 示例代码

源码地址:https://github.com/microsoft/DeepSpeed/tree/master/deepspeed/moe

其核心组件为deepspeed.moe.layer.MoEdeepspeed.moe.layers.gates 类。

1.MoE 类(deepspeed.moe.layer.MoE

作为入口类,集成了路由器、专家、通信逻辑:

class MoE(nn.Module):def __init__(self, hidden_size, experts=..., ep_size=..., k=1):self.experts = Experts()self.gate = TopKGate()...
  • ep_size: 每个专家组的并行数(Expert Parallelism)。
  • k: top-k gating.
  • 使用了通信优化如 All-to-All 分发样本。
2.构造函数 init

根据官方文档,MoE 的初始化签名如下,参数丰富且功能强大:

class MoE(nn.Module):def __init__(self,hidden_size: int,expert: nn.Module,num_experts: int = 1,ep_size: int = 1,k: int = 1,capacity_factor: float = 1.0,eval_capacity_factor: float = 1.0,min_capacity: int = 4,use_residual: bool = False,noisy_gate_policy: Optional[str] = None,drop_tokens: bool = True,use_rts: bool = True,use_tutel: bool = False,enable_expert_tensor_parallelism: bool = False,top2_2nd_expert_sampling: bool = True)
  • hidden_size:输入和输出的维度;
  • expert:作为子模块传入的专家网络(如 MLP);
  • num_experts:专家总数;
  • ep_size:专家并行维度;
  • k:选用 top‑k 路由;
  • capacity_factoreval_capacity_factor:训练/评估期间专家最大处理 token 数比例;
  • min_capacity:每个专家至少能接收的 token 数;
  • use_residual:是否启用 Residual MoE 结构;
  • noisy_gate_policydrop_tokensuse_rts:路由噪声、token 丢弃、随机选择;
  • enable_expert_tensor_parallelism:专家参数 tensor 切分;
  • top2_2nd_expert_sampling:top‑2 第二专家采样策略。

这些选项为 MoE 的训练/推理提供了高度灵活性

3.前向函数 forward

forward 函数定义如下:

def forward(self, hidden_states: Tensor, used_token: Optional[Tensor] = None) -> Tuple[Tensor, Tensor, Tensor]:

返回三元组 (output, l_aux, exp_counts),分别为输出、auxiliary loss、各专家激活次数

forward 函数的核心步骤可以总结为以下 5 部分:

def forward(self, hidden_states, used_token=None):# 1️⃣ Gating 阶段:计算每个 token 的专家 logits,并选出 top‑k 专家gates, load, indices, expert_capacity = self.gate(hidden_states, self.training)# gates: (B, k) 专家权重,load: auxiliary balance loss,indices: 专家索引# 2️⃣ Capacity 控制:根据 capacity_factor 限制每个专家最多处理的 token 数# 用 expert_capacity 来计算实际可接收的 token 数# 3️⃣ Dispatch 阶段:将 token 分发给对应专家dispatch_mask, combine_mask = create_masks(indices, expert_capacity)# dispatch_mask: 用于提取每个专家的 token# 重塑 hidden_states 方便通信:expert_inputs = torch.einsum("b h, b e -> e b h", hidden_states, dispatch_mask)# 4️⃣ all_to_all 分发 token:跨 GPU 路由 token 到对应专家所在 GPUexpert_inputs = all_to_all(expert_inputs, self.expert_parallel_group)# 5️⃣ 专家计算阶段:每个专家在本地 receive 的 token 上执行 forwardexpert_outputs = self.experts(expert_inputs)# 6️⃣ all_to_all 收集结果:各专家输出回传给原始 GPUexpert_outputs = all_to_all(expert_outputs, self.expert_parallel_group)# 7️⃣ 合并输出:将专家输出按照 token-group 重组回 batch 维度output = torch.einsum("e b h, b e -> b h", expert_outputs, combine_mask)return output, load, indices.bincount(...)
4.TopKGate 类(deepspeed.moe.layers.gates

实现 top-k 路由,并支持 noisy gate:

class TopKGate(nn.Module):def forward(self, input):logits = self.w_gating(input)topk_vals, topk_indices = torch.topk(logits, k)...

还包括负载均衡 loss。

5.Expert 通信部分

使用 all_to_all 通信分发数据,保证跨 GPU 的负载均衡和数据交换效率。

在多 GPU(分布式)训练中,如果我们有多个专家网络(Experts),这些专家可能是跨 GPU 分布的。举个例子:

  • 有 4 张 GPU,每张 GPU 上部署 2 个专家,共 8 个专家;
  • 假设 batch 里的一部分 token 需要被路由到第 3 个专家(在 GPU 2 上),另一部分需要被送到第 6 个专家(在 GPU 4 上);
  • 那么就必须跨 GPU 发送这些 token —— 所以通信效率就非常关键。

这时候就需要 all_to_all 机制来高效完成这个通信过程。

torch.distributed.all_to_all 是一种跨 GPU 的点对点通信机制,作用是每张 GPU 都给其他所有 GPU 发送一块数据,同时从其他 GPU 收到对应的数据块。

具体来说:

  • 每个进程(GPU)上都有自己的输入 token;
  • 每个进程根据路由器(Gate)的输出,将 token 分为 N 份,分别属于 N 个专家(也就是 N 个目标 GPU);
  • 然后用 all_to_all 一次性把这 N 份数据分发到对应的 GPU 上;
  • 所有专家完成前向计算后,再用 all_to_all 把结果发回。

参考 deepspeed/moe/utils/all_to_all.py

def all_to_all(input, group):# input shape: (num_local_experts, tokens_per_expert, hidden_size)output = torch.empty_like(input)torch.distributed.all_to_all_single(output, input, group=group)return output

通常输入需要 reshape 成:

[local_experts, tokens_per_expert, hidden_dim]

之后经过两次 all_to_all:

  • tokens 分发阶段:将 token 从本地发送到它所需的专家所在的 GPU;
  • 结果收集阶段:将处理后的输出再收集回原始的 GPU。

参考链接

Applying Mixture of Experts in LLM Architectures

https://www.cnblogs.com/theseventhson/p/18247463

需要 reshape 成:

[local_experts, tokens_per_expert, hidden_dim]

之后经过两次 all_to_all:

  • tokens 分发阶段:将 token 从本地发送到它所需的专家所在的 GPU;
  • 结果收集阶段:将处理后的输出再收集回原始的 GPU。

参考链接

Applying Mixture of Experts in LLM Architectures

https://www.cnblogs.com/theseventhson/p/18247463

https://zhuanlan.zhihu.com/p/1888975857147691214

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/bicheng/94996.shtml
繁体地址,请注明出处:http://hk.pswp.cn/bicheng/94996.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

如何将yolo训练图像数据库的某个分类的图像取出来

COCO 数据集 - Ultralytics YOLO 文档 比如我只想从数据集中取手机的图像&#xff0c;来用于我的训练&#xff0c;懒得自己一张一张标注&#xff0c;方法如下 # -*- coding: utf-8 -*- import json import os import shutil from pathlib import Path from tqdm import tqdm i…

【WPF】WPF 自定义控件实战:从零打造一个可复用的 StatusIconTextButton (含避坑指南)

&#x1f527; WPF 自定义控件实战&#xff1a;从零打造一个可复用的 StatusIconTextButton&#xff08;含避坑指南&#xff09;发布于&#xff1a;2025年8月29日 标签&#xff1a;WPF、C#、自定义控件、MVVM、Generic.xaml、属性绑定、TemplateBinding&#x1f4cc; 引言 在 W…

中国国际商会副秘书长徐梁一行到访国联股份

2025年08月27日&#xff0c;中国国际商会副秘书长徐梁等一行到访国联股份&#xff0c;国联股份创始人、CEO/总裁钱晓钧&#xff0c;国联股份副总裁、卫多多/纸多多CEO黄莎莎等热情招待来访一行&#xff0c;并展开深入交流。来访一行首先参观了国联股份数字经济展厅&#xff0c;…

换公司如何快速切入软件项目工程

一、前言 作为程序员&#xff0c;根据自身职业发展&#xff0c;会通过跳槽谋求更进一步的发展&#xff0c;这时进入新公司&#xff0c;接触全新的项目工程和业务&#xff0c;如何快速的切入&#xff0c;形成认识呢&#xff1f;就算不跳槽&#xff0c;公司业务调整&#xff0c;也…

Linux系统——EXT2 文件系统

磁盘文件 文件属性 文件内容文件内容 —— 数据块&#xff0c;文件属性 —— inodeLinux 文件在磁盘中的存储&#xff0c;是将 属性 与 内容 分开存储的内存&#xff1a;掉电易失&#xff0c;磁盘&#xff1a;永久性存储介质图片来自百度磁盘访问的基本单元&#xff1a;扇区 …

Qt中的锁(1)

Qt中的锁&#xff08;1&#xff09; 加锁&#xff0c;把多个要访问的公共资源通过锁保护起来&#xff0c;把并行执行变成串行执行&#xff0c; 多个线程执行加锁的对象得是同一个对象&#xff0c;不同对象不会互斥 代码&#xff1a;//添加一个static成员static int num;//创建锁…

数据结构 02(线性:顺序表)

目录 线性表 顺序表 概念与结构 动态顺序表的实现 头文件的创建 顺序表初始化 顺序表的扩容 尾插功能 头插功能 尾删功能 头删功能 查找功能 任意位置前插入 任意位置前删除 销毁 动态顺序表整体呈现 SeqList.h SeqList.c 线性表 线性表是n个具有相同特性的数…

自助餐厅:自主取餐的平衡术

自助餐厅&#xff0c;本质是通过 “固定客单价 自主取餐” 的模式&#xff0c;把 “吃什么、吃多少” 的选择权还给用户&#xff0c;同时用运营设计平衡 “用户体验” 与 “餐厅成本”—— 它不是 “让用户吃垮餐厅” 的游戏&#xff0c;而是餐饮行业里 “效率与体验结合” 的…

TypeScript: Reflect.ownKeys 操作(针对 Symbol)

Reflect.ownKeys 是 JavaScript ES6 引入的 Reflect API 中的一个方法&#xff0c;用于获取目标对象的所有自身属性键&#xff08;包括字符串键和 Symbol 键&#xff09;。1.基本概念&#xff1a;Reflect.ownKeys(target)&#xff1a;接受一个对象 target 作为参数&#xff0c;…

一般纳税人

目录 一文详解&#xff1a;什么是一般纳税人&#xff1f; 一、核心定义&#xff1a;什么是一般纳税人&#xff1f; 二、成为一般纳税人的两种途径 三、一般纳税人的关键特点与运作机制 四、一般纳税人的优点与缺点 五、与小规模纳税人的核心区别 六、企业应如何选择&…

@HAProxy 介绍部署使用

文章目录**1. HAProxy 简介****1.1 什么是 HAProxy&#xff1f;****1.2 核心特性****1.3 关键术语****2. 安装 HAProxy****2.1 在 Ubuntu/Debian 上安装****2.2 在 CentOS/RHEL/Rocky Linux/AlmaLinux 上安装****3. 配置与使用****3.1 核心配置文件结构****3.2 基础配置示例&am…

Two-Twer模型做歌曲智能推荐与规则算法对比的优缺点分析

基于规则与机器学习驱动的音乐推荐&#xff1a;核心差异分析1.推荐精度2. 个性化能力3. 模型适应性&#xff08;潜在特征关联发现&#xff09;4. 可扩展性与复杂性成本5. 冷启动/数据稀疏阶段表现6. 听感匹配与主观反馈1.推荐精度 规则推荐&#xff1a; 依赖预设的 if-then 逻…

【完整源码+数据集+部署教程】停车位状态检测系统源码和数据集:改进yolo11-DCNV2-Dynamic

背景意义 随着城市化进程的加快&#xff0c;城市交通拥堵问题日益严重&#xff0c;停车难成为了许多城市居民面临的普遍问题。有效的停车管理不仅可以提高城市交通的流动性&#xff0c;还能减少因寻找停车位而造成的时间浪费和环境污染。因此&#xff0c;开发一个高效的停车位状…

《Password Guessing Using Random Forest》论文解读

论文填补了传统统计方法&#xff08;如 PCFG、Markov&#xff09;与深度学习方法&#xff08;如 LSTM、GAN&#xff09;之间的研究空白&#xff0c;提出基于随机森林的口令猜测框架 RFGuess&#xff0c;覆盖三种核心猜测场景&#xff0c;为口令安全研究提供了全新技术路线。一、…

项目一系列-第9章 集成AI千帆大模型

第9章 集成AI千帆大模型 学习目标 能够说清楚健康评估模块在项目中的作用能够掌握千帆大模型的开通和对接能够掌握健康评估模块中的prompt提示词编写能够自主完成健康评估模块的接口开发 分析设计 需求说明 健康评估是指老人办理入住前需上传体检报告&#xff0c;由AI自动…

vben admin5组件文档(豆包版)---VbenTree

VbenTree 用法说明 VbenTree 是 Vben5 中基于 radix-vue 实现的树形组件&#xff0c;支持单选、多选、展开/折叠、权限控制等功能。以下是其核心用法说明&#xff1a; 1. 基础引入 import { VbenTree } from vben-core/shadcn-ui;2. 核心属性&#xff08;Props&#xff09;属性…

postman常用快捷键

作为一名IT程序猿&#xff0c;不懂一些工具的快捷方式&#xff0c;应该会被鄙视的吧。收集了一些Postman的快捷方式&#xff0c;大家一起动手操作~ 1小时postman接口测试从入门到精通教程简单操作 操作mac系统windows系统 打开新标签 ⌘TCtrl T关闭标签⌘WCtrl W强制关闭标签…

【物联网】什么是 DHT11(数字温湿度传感器)?

正面照片&#xff08;蓝色传感器朝上&#xff0c;针脚朝下&#xff09; 丝印标注非常清晰&#xff1a; 左边 → S &#x1f449; 信号 (DATA) 中间 → &#x1f449; VCC (电源&#xff0c;3.3V 或 5V) 右边 → - &#x1f449; GND (地) ✅ 正确接法&#xff08;Arduino Nano…

光谱相机在雾霾监测中有何优势?

光谱相机在雾霾监测中的优势主要体现在多维度数据采集和环境适应性方面&#xff0c;结合最新技术进展分析如下&#xff1a;一、核心优势‌穿透性监测能力‌ 短波红外&#xff08;SWIR&#xff09;波段可穿透雾霾颗粒&#xff0c;结合可见光成像实现雾霾浓度与能见度的同步监测&…

【c++】超好玩游戏

#include <iostream> #include <vector> #include <conio.h> #include <windows.h> #include <time.h>using namespace std;// 游戏常量 const int WIDTH 40; const int HEIGHT 20; const int PADDLE_WIDTH 5;// 方向枚举 enum Direction { S…