You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Numpy从对角线值创建数组栈的技术实现问题

解决Numpy中堆叠数组生成对角矩阵堆的问题

嘿,我来帮你搞定这个矩阵堆叠的难题!你遇到的问题其实是np.diag在处理二维输入时的行为和一维不同——它会提取对角线而非生成对角矩阵堆。下面分两部分解决你的问题:

一、更简洁的数组重复/堆叠方法

你之前用np.repeat(np.expand_dims(vals, axis=0), 5, axis=0)的写法没问题,但Numpy有更直观的np.tile函数可以简化:

import numpy as np
vals = np.array([1,2,3])
# 生成形状为(5, 3)的堆叠数组
vals_stack = np.tile(vals[np.newaxis, :], (5, 1))
# 或者用更简洁的None替代np.expand_dims
vals_stack = vals[None, :].repeat(5, axis=0)
print(vals_stack.shape)  # 输出: (5, 3)

np.tile的作用是“平铺”数组,第一个参数是要重复的基础数组,第二个参数是各维度的重复次数,比嵌套的repeat+expand_dims可读性更强。

二、无需循环生成堆叠对角矩阵

想要得到形状为(N, M, M)的对角矩阵堆(这里N=5,M=3),完全可以用Numpy的广播机制实现向量化操作,比循环效率高得多:

M = vals_stack.shape[1]
# 创建M×M的单位矩阵
eye_matrix = np.eye(M)
# 利用广播将每个一维数组转为对角矩阵
mat_stack = vals_stack[:, :, np.newaxis] * eye_matrix
print(mat_stack.shape)  # 输出: (5, 3, 3)

原理说明:

  • vals_stack[:, :, np.newaxis]将原数组形状从(5,3)转为(5,3,1)
  • 当它和形状为(3,3)的单位矩阵相乘时,Numpy会自动广播:每个(3,1)的向量会和单位矩阵的每一列相乘,最终生成(5,3,3)的对角矩阵堆。

你可以验证一下结果,比如mat_stack[0]就是np.diag([1,2,3]),完全符合需求。

如果偏好更紧凑的写法,也可以用np.einsum实现:

mat_stack = np.einsum('ni,jk->nij', vals_stack, np.eye(M))

效果和广播方法一致,不过广播的写法更直观易懂。

为什么不用循环?

循环在Numpy中效率极低,尤其是当堆叠数量N很大时,向量化操作能利用Numpy的底层优化(比如C语言实现),运行速度会快几个数量级。

内容的提问来源于stack exchange,提问作者koxx

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.13 08:57:04