【问题标题】:Combining NumPy arrays组合 NumPy 数组
【发布时间】:2011-10-08 02:13:14
【问题描述】:

我有两个 20x100x3 NumPy 数组,我想将它们组合成一个 40 x 100 x 3 数组,也就是说,只需在数组中添加更多行。我对我想要哪个函数感到困惑:它是 vstack、hstack、column_stack 还是其他什么?

【问题讨论】:

    标签: python arrays numpy


    【解决方案1】:

    我相信你想要的是 vstack

    p=array_2
    q=array_2
    p=numpy.vstack([p,q])
    

    【讨论】:

    • 不知道为什么我第一次访问该页面时没有显示您的答案。 +1 建议先使用 vstack。
    • 请注意,文档建议现在使用 stackconcatenate,并且仅支持 vstack 以实现向后兼容性,请参阅:docs.scipy.org/doc/numpy-1.13.0/reference/generated/…
    【解决方案2】:

    最好的学习方法之一是实验,但我想说你想要np.vstack,尽管还有其他方法可以做同样的事情:

    a = np.ones((20,100,3))
    b = np.vstack((a,a)) 
    
    print b.shape # (40,100,3)
    

    b = np.concatenate((a,a),axis=0)
    

    编辑

    请注意,在我的机器上,对于 OP 问题中的大小数组,我发现 np.concatenatenp.vstack 快大约 2 倍

    In [172]: a = np.random.normal(size=(20,100,3))
    
    In [173]: c = np.random.normal(size=(20,100,3))
    
    In [174]: %timeit b = np.concatenate((a,c),axis=0)
    100000 loops, best of 3: 13.3 us per loop
    
    In [175]: %timeit b = np.vstack((a,c))
    10000 loops, best of 3: 26.1 us per loop
    

    【讨论】:

    • 我可能是愚蠢的,因为我没有使用太多的 timeit,但是连接不会占用 10 倍的循环吗?
    • @Giltech,虽然 timeit 使用 10 倍以上的循环来对 np.concatenate 进行基准测试(它似乎是自动选择的),但这里重要的数字是每个循环的时间
    • 您应该注意因子 2。您的测试用例包含 6000 个项目的小数组,并且在我们的范围内。简单地将输入数组扩展到 (20,10000,3) 会导致 6.62 ms per loop6.38 ms per loop,仍然有优势直接使用连接。所以对于大数组来说,差异并不重要。
    • @EnnoGröper 好点。当性能很重要时,应该始终执行自己的基准测试/进行自己的分析。考虑到 OP 系统的大小,我只是建议一种特定的方法。
    【解决方案3】:

    值得一提的是

        np.concatenate((a1, a2, ...), axis=0) 
    

    是一般形式,vstack 和 hstack 是具体情况。我发现最容易知道我想要堆叠哪个维度并将其作为参数提供给 np.concatenate。

    【讨论】:

      【解决方案4】:

      我在 r_ 和 vstack 之间尝试了一个小基准测试,结果非常有趣:

      import numpy as np
      
      NCOLS = 10
      NROWS = 2
      NMATRICES = 10000
      
      def mergeR(matrices):
          result = np.zeros([0, NCOLS])
      
          for m in matrices:
              result = np.r_[ result, m]
      
      def mergeVstack(matrices):
          result = np.vstack(matrices)
      
      def main():
          matrices = tuple( np.random.random([NROWS, NCOLS]) for i in xrange(NMATRICES) )
          mergeR(matrices)
          mergeVstack(matrices)
      
          return 0
      
      if __name__ == '__main__':
          main()
      

      然后我运行分析器:

      python -m cProfile -s cumulative np_merge_benchmark.py
      

      结果:

      ncalls  tottime  percall  cumtime  percall filename:lineno(function)
      ...
           1    0.579    0.579    4.139    4.139 np_merge_benchmark.py:21(mergeR)
      ...
           1    0.000    0.000    0.054    0.054 np_merge_benchmark.py:27(mergeVstack)
      

      所以 vstack 方式快 77 倍!

      【讨论】:

        【解决方案5】:

        对了,还有r_

        >>> from scipy import *
        >>> a = rand(20,100,3)
        >>> b = rand(20,100,3)
        >>> a.shape
        (20, 100, 3)
        >>> b.shape
        (20, 100, 3)
        >>> r_[a,b].shape
        (40, 100, 3)
        >>> (r_[a,b] == vstack([a,b])).all()
        True
        

        【讨论】:

          猜你喜欢
          • 2021-11-24
          • 1970-01-01
          • 2021-09-05
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2013-02-01
          • 2019-06-21
          • 2018-01-14
          相关资源
          最近更新 更多