Python numpy.insert的性能取决于阵列大小-解决方法?
使用下面的代码,我得到的印象是,插入numpy数组取决于数组大小 对于此性能限制,是否有任何基于numpy的变通方法(或者也有非基于numpy的变通方法)Python numpy.insert的性能取决于阵列大小-解决方法?,python,performance,numpy,Python,Performance,Numpy,使用下面的代码,我得到的印象是,插入numpy数组取决于数组大小 对于此性能限制,是否有任何基于numpy的变通方法(或者也有非基于numpy的变通方法) 这与numpy的工作方式有关。对于每个插入操作,它将获取整个阵列并将其存储在新的位置。我建议使用listappend并将其转换为numpy数组。这可能与numpy的工作方式有关。对于每个插入操作,它将获取整个阵列并将其存储在新的位置。我建议使用listappend并将其转换为numpy数组。可能与您的方法重复: In [18]: arr =
这与
numpy
的工作方式有关。对于每个插入操作,它将获取整个阵列并将其存储在新的位置。我建议使用list
append并将其转换为numpy
数组。这可能与numpy的工作方式有关。对于每个插入操作,它将获取整个阵列并将其存储在新的位置。我建议使用list
append并将其转换为numpy
数组。可能与您的方法重复:
In [18]: arr = np.array([])
In [19]: for i in range(1000):
...: arr = np.insert(arr, arr.shape[0],[1,2,3])
...:
In [20]: arr.shape
Out[20]: (3000,)
In [21]: %%timeit
...: arr = np.array([])
...: for i in range(1000):
...: arr = np.insert(arr, arr.shape[0],[1,2,3])
...:
31.9 ms ± 194 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)
将其与连接进行比较:
In [22]: %%timeit
...: arr = np.array([])
...: for i in range(1000):
...: arr = np.concatenate((arr, [1,2,3]))
...:
5.49 ms ± 20.6 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
并通过列表扩展:
In [23]: %%timeit
...: alist = []
...: for i in range(1000):
...: alist.extend([1,2,3])
...: arr = np.array(alist)
384 µs ± 13.2 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
我们不鼓励使用串联
(或np.append
),因为它速度慢,并且很难初始化。列表附加或扩展速度更快。使用insert
比使用concatenate
更糟糕
concatenate
每次生成一个全新的数组<代码>插入也可以这样做,但由于它的设计目的是将新值放在原始值的任何位置,因此它要复杂得多,因此速度较慢。如果你不相信我,看看它的代码
列表
是为增长而设计的;新项目通过简单的对象(指针)插入到具有增长的缓冲区中来添加。也就是说,增长发生在适当的地方
插入完整数组也很好:
In [27]: %%timeit
...: arr = np.zeros((1000,3),int)
...: for i in range(1000):
...: arr[i,:] = [1,2,3]
...: arr = arr.ravel()
1.69 ms ± 9.47 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
你的做法:
In [18]: arr = np.array([])
In [19]: for i in range(1000):
...: arr = np.insert(arr, arr.shape[0],[1,2,3])
...:
In [20]: arr.shape
Out[20]: (3000,)
In [21]: %%timeit
...: arr = np.array([])
...: for i in range(1000):
...: arr = np.insert(arr, arr.shape[0],[1,2,3])
...:
31.9 ms ± 194 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)
将其与连接进行比较:
In [22]: %%timeit
...: arr = np.array([])
...: for i in range(1000):
...: arr = np.concatenate((arr, [1,2,3]))
...:
5.49 ms ± 20.6 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
并通过列表扩展:
In [23]: %%timeit
...: alist = []
...: for i in range(1000):
...: alist.extend([1,2,3])
...: arr = np.array(alist)
384 µs ± 13.2 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
我们不鼓励使用串联
(或np.append
),因为它速度慢,并且很难初始化。列表附加或扩展速度更快。使用insert
比使用concatenate
更糟糕
concatenate
每次生成一个全新的数组<代码>插入也可以这样做,但由于它的设计目的是将新值放在原始值的任何位置,因此它要复杂得多,因此速度较慢。如果你不相信我,看看它的代码
列表
是为增长而设计的;新项目通过简单的对象(指针)插入到具有增长的缓冲区中来添加。也就是说,增长发生在适当的地方
插入完整数组也很好:
In [27]: %%timeit
...: arr = np.zeros((1000,3),int)
...: for i in range(1000):
...: arr[i,:] = [1,2,3]
...: arr = arr.ravel()
1.69 ms ± 9.47 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
而不是从一个小数组开始,并将块插入其中,您是否考虑创建数组的完整大小和最终大小,然后将值赋给该数组的不同部分?只要逻辑允许,与多次插入相比,这总是一个更快的选择。最后,如果你还剩下一个不需要的部分,你甚至可以执行一个单独的NoMy.Delphi操作,而不是从一个小数组开始并将块插入其中,你是否考虑创建数组的完整和最终大小,然后将值赋值到该数组的不同部分?只要逻辑允许,与多次插入相比,这总是一个更快的选择。最后,如果仍然只剩下一个不需要的部分,您甚至可以执行一个numpy.delete操作。