如何实现从3D numpy数组中选取N组随机数据的向量化操作
Numpy 3D数组按规则随机抽样的向量化实现方案
核心实现思路
利用Numpy高级索引的广播特性,一次性完成所有组的抽样,完全避免Python级循环。
实现代码
import numpy as np # 原始3D数组,示例形状为 (3,4,7) a = np.array([[[ 0. , 4. , 8. , 12. , 16. , 20. , 24. ], [ 1. , 5. , 9. , 13. , 17. , 21. , 25. ], [ 2. , 6. , 10. , 14. , 18. , 22. , 26. ], [ 3. , 7. , 11. , 15. , 19. , 23. , 27. ]], [[ 0.1, 4.1, 8.1, 12.1, 16.1, 20.1, 24.1], [ 1.1, 5.1, 9.1, 13.1, 17.1, 21.1, 25.1], [ 2.1, 6.1, 10.1, 14.1, 18.1, 22.1, 26.1], [ 3.1, 7.1, 11.1, 15.1, 19.1, 23.1, 27.1]], [[ 0.2, 4.2, 8.2, 12.2, 16.2, 20.2, 24.2], [ 1.2, 5.2, 9.2, 13.2, 17.2, 21.2, 25.2], [ 2.2, 6.2, 10.2, 14.2, 18.2, 22.2, 26.2], [ 3.2, 7.2, 11.2, 15.2, 19.2, 23.2, 27.2]]]) N = 2 # 要抽取的组数 M = a.shape[0] # axis0的长度 K = a.shape[1] # axis1的可选索引范围长度 # 1. 生成随机索引,形状为 (N, M),每个值的范围是0~K-1 # 若已有手动指定的idx,直接替换这一步即可 idx = np.random.randint(0, K, size=(N, M)) # 示例中手动指定的idx:idx = np.array([[0, 2, 1], [1, 3, 3]]) # 2. 高级索引一次性抽取所有数据,输出形状为 (N, M, L),L是axis2的长度 result = a[np.arange(M)[np.newaxis, :], idx, :] print(result)
原理解释
- 轴0的索引
np.arange(M)[np.newaxis, :]形状为(1, M),和形状为(N, M)的随机索引idx广播后维度匹配 - 对应位置的索引组合为
(j, idx[i,j]),刚好对应要求的「第i组,轴0取j,轴1取idx[i,j],轴2取全部」的规则 - 整个操作全由Numpy底层C实现,即便N取10000也能在毫秒级完成,性能远高于嵌套Python循环
内容的提问来源于stack exchange,提问作者AlexP
相关产品推荐
相关产品推荐

