
从矩阵乘法开始手撕多模态大模型 - 完整版引言多模态大模型的数学根基多模态大模型如 CLIP、LLaVA、Flamingo之所以能同时理解图像和文本其核心在于张量运算的统一性。无论是图像像素、文本词向量还是注意力分数底层都用矩阵乘法来建模关联。本篇文章将从最基础的矩阵乘法出发逐步构建一个简化但可运行的多模态模型涵盖图像特征提取、文本嵌入、多模态融合等关键环节。通过手撕代码你将看到矩阵乘法如何成为连接不同模态数据的桥梁。## 矩阵乘法的本质从线性变换到特征映射在深度学习中矩阵乘法YXWbY XW bYXWb是最基本的操作。其中XXX是输入特征WWW是权重矩阵YYY是输出特征。对于多模态模型不同模态的输入如图像的像素矩阵、文本的 token 序列都可以通过矩阵乘法映射到共享的隐空间。关键洞察多模态对齐的本质是让图像特征和文本特征在同一个高维空间中的距离度量有意义。而这需要两个模态的矩阵乘法权重相互协调。下面是一个简单的 Python 实现演示如何用矩阵乘法将图像 patch 和文本 token 映射到 128 维的共享空间pythonimport numpy as np# 1. 模拟多模态输入# 图像: 假设有 4 个 patch每个 patch 原始特征维度为 256image_patches np.random.randn(4, 256) # (num_patches, dim_image)# 文本: 假设有 3 个 token每个 token 原始特征维度为 512text_tokens np.random.randn(3, 512) # (num_tokens, dim_text)# 2. 定义可训练的投影矩阵 (共享隐空间维度为 128)shared_dim 128W_image np.random.randn(256, shared_dim) * 0.1 # 图像投影W_text np.random.randn(512, shared_dim) * 0.1 # 文本投影# 3. 执行矩阵乘法将不同模态映射到共享空间image_features image_patches W_image # 4 x 128text_features text_tokens W_text # 3 x 128print(图像特征矩阵形状:, image_features.shape)print(文本特征矩阵形状:, text_features.shape)print(第一个图像patch的128维向量:, image_features[0, :5]) # 仅打印前5个元素输出示例图像特征矩阵形状: (4, 128)文本特征矩阵形状: (3, 128)第一个图像patch的128维向量: [ 0.234 -0.567 0.891 -0.123 0.456]这里我们通过两个独立的矩阵乘法将不同维度的输入映射到相同维度的共享空间。这正是多模态预训练的第一步。## 构建多模态融合的核心交叉注意力机制多模态大模型的关键在于如何让图像特征和文本特征互相“看见”。最常用的方法是交叉注意力Cross-Attention它通过矩阵乘法计算两个模态之间的相似度然后用加权和融合信息。交叉注意力的数学形式为[\text{Attention}(Q, K, V) \text{softmax}\left(\frac{QK^T}{\sqrt{d_k}}\right) V]其中QQQ来自一个模态如文本KKK和VVV来自另一个模态如图像。这里的QKTQK^TQKT就是矩阵乘法它衡量每个文本 token 与每个图像 patch 的相关性。下面实现一个简化版的交叉注意力模块pythonimport numpy as npdef cross_attention(query, key, value): 交叉注意力机制 query: (num_queries, d_model) 来自模态A key: (num_keys, d_model) 来自模态B value: (num_keys, d_model) 来自模态B d_k query.shape[-1] # 核心矩阵乘法: Q K^T 计算相似度分数 scores query key.T # (num_queries, num_keys) # 缩放防止softmax梯度爆炸 scores scores / np.sqrt(d_k) # 软归一化得到注意力权重 attention_weights np.exp(scores) / np.sum(np.exp(scores), axis-1, keepdimsTrue) # 加权求和: 权重 value output attention_weights value # (num_queries, d_model) return output, attention_weights# 模拟多模态特征# 文本特征作为query (3个token)text_q np.random.randn(3, 64)# 图像特征作为key和value (4个patch)image_k np.random.randn(4, 64)image_v np.random.randn(4, 64)# 执行交叉注意力fused_features, attn cross_attention(text_q, image_k, image_v)print(融合后的文本特征 (每个token融合了图像信息):)print(fused_features.shape)print(注意力权重 (3个token对4个patch的注意力分布):)print(np.round(attn, 3))输出示例融合后的文本特征 (每个token融合了图像信息):(3, 64)注意力权重 (3个token对4个patch的注意力分布):[[0.213 0.307 0.254 0.226] [0.258 0.289 0.231 0.222] [0.245 0.271 0.264 0.22 ]]这个简单的矩阵乘法操作query key.T揭示了多模态融合的本质通过计算跨模态的相似度让文本特征动态地从图像中提取相关信息。在实际的大模型中这样的交叉注意力层会堆叠多次并配合残差连接和层归一化。## 端到端的多模态推理示例现在我们将上述两个步骤投影 交叉注意力组合成一个完整的推理流程。假设我们有一个训练好的模型这里用随机权重模拟输入一张“图像”和一段“文本”输出融合后的特征用于分类。pythonimport numpy as npclass SimpleMultiModalModel: def __init__(self, img_dim256, text_dim512, shared_dim128): # 图像和文本的投影矩阵 self.W_img np.random.randn(img_dim, shared_dim) * 0.1 self.W_txt np.random.randn(text_dim, shared_dim) * 0.1 # 用于交叉注意力的QKV投影 (简化版使用同一个矩阵) self.W_q np.random.randn(shared_dim, shared_dim) * 0.1 self.W_k np.random.randn(shared_dim, shared_dim) * 0.1 self.W_v np.random.randn(shared_dim, shared_dim) * 0.1 def forward(self, img_patches, text_tokens): # Step1: 映射到共享空间 img_feat img_patches self.W_img # (num_patches, shared_dim) txt_feat text_tokens self.W_txt # (num_tokens, shared_dim) # Step2: 计算QKV (文本作为query, 图像作为key和value) Q txt_feat self.W_q K img_feat self.W_k V img_feat self.W_v # Step3: 交叉注意力融合 d_k Q.shape[-1] scores Q K.T / np.sqrt(d_k) attn np.exp(scores) / np.sum(np.exp(scores), axis-1, keepdimsTrue) fused attn V # (num_tokens, shared_dim) # Step4: 全局池化得到单一向量 (用于分类) global_feat np.mean(fused, axis0) # (shared_dim,) return global_feat# 模拟多模态输入img_patches np.random.randn(4, 256) # 4个图像patchtext_tokens np.random.randn(3, 512) # 3个文本tokenmodel SimpleMultiModalModel()output model.forward(img_patches, text_tokens)print(最终多模态表示向量 (128维):)print(形状:, output.shape)print(前10个元素:, np.round(output[:10], 4))输出示例最终多模态表示向量 (128维):形状: (128,)前10个元素: [ 0.0123 -0.0456 0.0789 -0.0123 0.0567 -0.0345 0.0891 -0.0678 0.0234 -0.0912]这个向量可以被送入一个简单的分类器如线性层Softmax来完成图像-文本匹配、视觉问答等任务。虽然这里的权重是随机的但通过训练调整所有矩阵乘法的权重模型可以学会在共享空间中对齐猫的图像和“猫”这个词。## 深入原理矩阵乘法如何驱动多模态学习从上述代码中我们可以提炼出三个关键原理1.空间映射的线性代数本质每个模态的投影矩阵WWW定义了从原始特征空间到共享空间的线性变换。训练过程实际上是在调整这些变换的方向使得同一语义在不同模态中的投影向量具有高余弦相似度。2.注意力机制中的矩阵秩交叉注意力中的QKTQK^TQKT矩阵的秩决定了模型能捕获的跨模态关联模式数量。当dkd_kdk较小时如64这个矩阵通常是低秩的意味着模型倾向于学习少数强关联模式如“狗”对应狗的耳朵、尾巴等。3.梯度流动的数学路径所有矩阵乘法的梯度可以通过链式法则反向传播。例如图像投影矩阵WimgW_{img}Wimg的梯度会同时受到图像自身特征和文本特征通过交叉注意力的影响从而实现多模态协同学习。## 总结多模态大模型看似复杂但底层就是一系列精心设计的矩阵乘法。从最初的模态投影input W到跨模态注意力Q K^T再到最终的融合输出attn V每一步都是线性代数在深度学习中的优雅应用。通过本文的代码实践你应该能理解- 如何用矩阵乘法将不同维度的输入统一到共享空间- 交叉注意力如何通过矩阵乘法实现跨模态信息交互- 一个完整的多模态推理流程如何由多个矩阵乘法组合而成当你下次看到“多模态大模型”这个术语时不妨在脑海中还原出这些矩阵乘法的形状和流动这就是连接视觉和语言的最朴素、最强大的数学工具。