用于在python中循环数组-来自matlab

用于在python中循环数组-来自matlab,python,arrays,matlab,for-loop,numpy,Python,Arrays,Matlab,For Loop,Numpy,假设您有以下MATLAB代码部分,在矩阵迭代时循环并修改矩阵中的索引值: x = zeros(parts,2); for i = 1:parts x(i,1) = (i-1)*L + 1; x(i,2) = i*L; end 现在假设您是一个python noob,并且已经做到了这一点: v = np.zeros((parts,2)) for x in xrange(0,N1/L): 其中零件和N1/L是预定义的整数值。 我在python中对索引和for循环做了一些搜索,但是我很难理解如何引

假设您有以下MATLAB代码部分,在矩阵迭代时循环并修改矩阵中的索引值:

x = zeros(parts,2);
for i = 1:parts
x(i,1) = (i-1)*L + 1;
x(i,2) = i*L;
end
现在假设您是一个python noob,并且已经做到了这一点:

v = np.zeros((parts,2))
for x in xrange(0,N1/L):
其中零件和N1/L是预定义的整数值。
我在python中对索引和for循环做了一些搜索,但是我很难理解如何引用特定的索引并在for循环中修改它们。如果有人能告诉我正确的方向,让我理解如何攻击代码的下一部分,我将不胜感激。

Matlab代码的直译将是

import numpy as np
x = np.zeros((parts, 2))
for i in range(parts):
    x[i,0] = i*L + 1
    x[i,1] = (i+1)*L
请注意,Matlab使用基于1的索引,而Python使用基于0的索引。这就解释了1在哪里出现的差异

但是,在使用NumPy时,如果避免对数组逐个元素进行修改,您将获得更好的性能。相反,您应该设法用尽可能少的NumPy运算符或函数调用来表示计算,这会立即影响整个数组。通过这样做,您可以尽可能多地卸载NumPy底层的快速C/Fortran编译函数调用,并减少执行较慢Python代码所花费的时间

这通常意味着您希望避免使用Python for循环,因为循环意味着存在 将有许多Python语句要执行

例如,表达上述计算的更好方法是

x = np.zeros((parts, 2))
x[:, 0] = np.arange(1, parts*L, L)
x[:, 1] = x[:, 0] + L - 1
请注意,
x
中的值仅使用两个赋值填充。每个 赋值影响整列的
x
“一次全部”


要了解基于数组的操作的不同之处, 下面是使用
parts=10000
L=3
进行的()时间IT测试:

In [16]: %%timeit
   ....: x = np.zeros((parts, 2))
         x[:, 0] = np.arange(1, parts*L, L)
         x[:, 1] = x[:, 0] + L - 1
10000 loops, best of 3: 51.9 µs per loop

In [17]: %%timeit
   ....: x = np.zeros((parts, 2))
         for i in range(parts):
             x[i,0] = i*L + 1
             x[i,1] = (i+1)*L
100 loops, best of 3: 3.58 ms per loop

这种循环在早期版本的MATLAB中也很糟糕。这非常有用,我非常感谢。我唯一感到困惑的是np.arange的参数。根据文件,第二个参数是“停止”标记。为什么是parts*L而不仅仅是parts?最好在Python交互式会话中试用
np.arange(1,parts,L)
np.arange(1,parts*L,L)
来了解
parts
L
的具体值。我相信你很快就会明白的。第二个参数,
stop
值始终略大于
np.arange
返回的数组中的最后一个值。与
range
np.arange
不包括
stop
值。因为我们希望最后一个值是
(parts-1)*L+1
,所以
parts*L
停止
值就可以了,因为我们用步长
L
递增<代码>部分*L-L+2也可以工作,但这是不必要的复杂。