Numpy与Matlab科学计算对比
MATLAB®和NumPy / SciPy有很多共同之处。但是有很多不同之处。创建NumPy和SciPy是为了用Python最自然的方式进行数值和科学计算,而不是MATLAB®克隆。
关键的差异
MATLAB | NumPy |
---|---|
在MATLAB®中,基本数据类型是双精度浮点数的多维数组。大多数表达式采用这样的数组并返回这样的数 对这些数组的2-D实例的操作被设计成或多或少地像线性代数中的矩阵运算。 | 在NumPy中,基本类型是多维的array。包括2D在内的所有维度中对这些数组的操作是逐元素操作。人们需要使用线性代数的特定函数(尽管对于矩阵乘法,可以@在python 3.5及更高版本中使用运算符)。 |
MATLAB®使用基于1(一)的索引。使用(1)找到序列的初始元素。 请参阅备注 | Python使用基于0(零)的索引。使用[0]找到序列的初始元素。 |
MATLAB®的脚本语言是为执行线性代数而创建的。基本矩阵操作的语法很好而且干净,但是用于添加GUI和制作完整应用程序的API或多或少都是事后的想法。 | NumPy基于Python,它从一开始就被设计成一种优秀的通用编程语言。虽然Matlab的一些数组操作的语法比NumPy更紧凑,但NumPy(由于是Python的附加组件)可以做许多Matlab不能做的事情,例如正确处理矩阵堆栈。 |
在MATLAB®中,数组具有按值传递的语义,并具有惰性写入时复制方案,以防止在实际需要之前实际创建副本。切片操作复制数组的一部分。 | 在NumPy数组中有传递引用语义。切片操作是对数组的视图。 |
MATLAB 和 NumPy粗略的功能对应表
一般功能的对应表
MATLAB | NumPy | 注释 |
---|---|---|
help func | info(func)或者help(func)或func?(在IPython的) | 获得函数func的帮助 |
which func | 请参阅备注 | 找出func定义的位置 |
type func | source(func)或者func??(在Ipython中) | func的打印源(如果不是本机函数) |
a && b | a and b | 短路逻辑AND运算符(Python本机运算符); 只有标量参数 |
a | b | |
1i,1j, 1i,1j | 1j | 复数 |
eps | np.spacing(1) | 1与最近的浮点数之间的距离。 |
ode45 | scipy.integrate.solve_ivp(f) | 将ODE与Runge-Kutta 4,5集成 |
ode15s | scipy.integrate.solve_ivp(f, method='BDF') | 将ODE与BDF方法集成 |
线性代数功能对应表
MATLAB | NumPy | 注释 |
---|---|---|
ndims(a) | ndim(a) 要么 a.ndim | 获取数组的维数 |
numel(a) | size(a) 要么 a.size | 获取数组的元素数 |
size(a) | shape(a) 要么 a.shape | 得到矩阵的“大小” |
size(a,n) | a.shape[n-1] | 获取数组第n维元素的数量a。(请注意,MATLAB®使用基于1的索引,而Python使用基于0的索引,请参阅备注) |
[ 1 2 3; 4 5 6 ] | array([[1.,2.,3.], [4.,5.,6.]]) | 2x3矩阵文字 |
[ a b; c d ] | block([[a,b], [c,d]]) | 从块构造一个矩阵a,b,c,和d |
a(end) | a[-1] | 访问1xn矩阵中的最后一个元素 a |
a(2,5) | a[1,4] | 访问第二行,第五列中的元素 |
a(2,:) | a[1] 或者 a[1,:] | a的第二行 |
a(1:5,:) | a[0:5]或a[:5]或a[0:5,:] | 前五行 a |
a(end-4:end,:) | a[-5:] | a的最后五行 |
a(1:3,5:9) | a[0:3][:,4:9] | a的第一至第三行与第五至第九列交叉的元素。这提供了只读访问权限。 |
a([2,4,5],[1,3]) | a[ix_([1,3,4],[0,2])] | 第2,4,5行与第1,3列交叉的元素。这允许修改矩阵,并且不需要常规切片。 |
a(3:2:21,:) | a[ 2:21:2,:] | 返回a的第3行与第21行之间每隔一行的行,即第3行与第21行之间的a的奇数行 |
a(1:2:end,:) | a[ ::2,:] | 返回a的奇数行 |
a(end: -1:1,:) 要么 flipud(a) | a[ ::-1,:] | 以相反的顺序排列的a的行 |
a([1:end 1],: ) | a[r_[:len(a),0]] | a 的第一行添加到a的末尾行的副本 |
a.' | a.transpose() 要么 a.T | 转置 a |
a' | a.conj().transpose() 要么 a.conj().T | 共轭转置 a |
a * b | a @ b | 矩阵乘法 |
a .* b | a * b | 元素乘法 |
a./b | a/b | 元素除法 |
a.^3 | a**3 | 元素取幂 |
(a>0.5) | (a>0.5) | 其i,jth元素为(a_ij> 0.5)的矩阵。Matlab结果是一个0和1的数组。NumPy结果是布尔值的数组False和True。 |
find(a>0.5) | nonzero(a>0.5) | 找到a中所有大于0.5的元素的线性位置 |
a(:,find(v>0.5)) | a[:,nonzero(v>0.5)[0]] | 提取a中向量v> 0.5的对应的列 |
a(:,find(v>0.5)) | a[:,v.T>0.5] | 提取a中向量v> 0.5的对应的列 |
a(a<0.5)=0 | a[a<0.5]=0 | a中小于0.5的元素赋值为0 |
a .* (a>0.5) | a * (a>0.5) | 返回一个数组,若a中对应位置元素大于0.5,取该元素的值;若a中对应元素<=0.5,取值0 |
a(: ) = 3 | a[:] = 3 | 将所有值设置为相同的标量值 |
y=x | y = x.copy() | numpy通过引用分配 |
y=x(2,:) | y = x[1,:].copy() | numpy切片是参考 |
y=x(: ) | y = x.flatten() | 将数组转换为向量(请注意,这会强制复制) |
1:10 | arange(1.,11.)或r_[1.:11.]或 r_[1:10:10j] | 创建一个增加的向量,步长为默认值1(参见备注) |
0:9 | arange(10.)或 r_[:10.]或 r_[:9:10j] | 创建一个增加的向量,步长为默认值1(参见注释范围) |
[1:10]' | arange(1.,11.)[:, newaxis] | 创建列向量 |
zeros(3,4) | zeros((3,4)) | 3x4二维数组,充满64位浮点零 |
zeros(3,4,5) | zeros((3,4,5)) | 3x4x5三维数组,全部为64位浮点零 |
ones(3,4) | ones((3,4)) | 3x4二维数组,充满64位浮点数 |
eye(3) | eye(3) | 3x3单位矩阵 |
diag(a) | diag(a) | 返回a的对角元素 |
diag(a,0) | diag(a,0) | 方形对角矩阵,其非零值是元素 a |
rand(3,4) | random.rand(3,4) 要么 random.random_sample((3, 4)) | 随机3x4矩阵 |
linspace(1,3,4) | linspace(1,3,4) | 4个等间距的样本,介于1和3之间 |
[x,y]=meshgrid(0:8,0:5) | mgrid[0:9.,0:6.] 要么 meshgrid(r_[0:9.],r_[0:6.] | 两个2D数组:一个是x值,另一个是y值 |
ogrid[0:9.,0:6.] 要么 ix_(r_[0:9.],r_[0:6.] | 在网格上评估函数的最佳方法 | |
[x,y]=meshgrid([1,2,4],[2,4,5]) | meshgrid([1,2,4],[2,4,5]) | |
ix_([1,2,4],[2,4,5]) | 在网格上评估函数的最佳方法 | |
repmat(a, m, n) | tile(a, (m, n)) | 用n份副本创建m a |
[a b] | concatenate((a,b),1)或者hstack((a,b))或 column_stack((a,b))或c_[a,b] | 连接a和的列b |
[a; b] | concatenate((a,b))或vstack((a,b))或r_[a,b] | 连接a和的行b |
max(max(a)) | a.max() | 最大元素a(对于matlab,ndims(a)<= 2) |
max(a) | a.max(0) | 每列矩阵的最大元素 a |
max(a,[],2) | a.max(1) | 每行矩阵的最大元素 a |
max(a,b) | maximum(a, b) | 比较a和b逐个元素,并返回每对中的最大值 |
norm(v) | sqrt(v @ v) 要么 np.linalg.norm(v) | L2矢量的规范 v |
a & b | logical_and(a,b) | 逐个元素AND运算符(NumPy ufunc)请参阅备注LOGICOPS |
a | b | logical_or(a,b) |
bitand(a,b) | a & b | 按位AND运算符(Python native和NumPy ufunc) |
bitor(a,b) | a | b |
inv(a) | linalg.inv(a) | 方阵的逆 a |
pinv(a) | linalg.pinv(a) | 矩阵的伪逆 a |
rank(a) | linalg.matrix_rank(a) | 二维数组/矩阵的矩阵秩 a |
a\b | linalg.solve(a,b)如果a是正方形; linalg.lstsq(a,b) 除此以外 | ax = b的解为x |
b/a | 解决aT xT = bT | xa = b的解为x |
[U,S,V]=svd(a) | U, S, Vh = linalg.svd(a), V = Vh.T | 奇异值分解 a |
chol(a) | linalg.cholesky(a).T | 矩阵的cholesky分解(chol(a)在matlab中返回一个上三角矩阵,但linalg.cholesky(a)返回一个下三角矩阵) |
[V,D]=eig(a) | D,V = linalg.eig(a) | 特征值和特征向量 a |
[V,D]=eig(a,b) | D,V = scipy.linalg.eig(a,b) | 特征值和特征向量a,b |
[V,D]=eigs(a,k) | 找到k最大的特征值和特征向量a | |
[Q,R,P]=qr(a,0) | Q,R = scipy.linalg.qr(a) | QR分解 |
[L,U,P]=lu(a) | L,U = scipy.linalg.lu(a) 要么 LU,P=scipy.linalg.lu_factor(a) | LU分解(注:P(Matlab)==转置(P(numpy))) |
conjgrad | scipy.sparse.linalg.cg | 共轭渐变求解器 |
fft(a) | fft(a) | 傅立叶变换 a |
ifft(a) | ifft(a) | 逆傅立叶变换 a |
sort(a) | sort(a) 要么 a.sort() | 对矩阵进行排序 |
[b,I] = sortrows(a,i) | I = argsort(a[:,i]), b=a[I,:] | 对矩阵的行进行排序 |
regress(y,X) | linalg.lstsq(X,y) | 多线性回归 |
decimate(x, q) | scipy.signal.resample(x, len(x)/q) | 采用低通滤波的下采样 |
unique(a) | unique(a) | |
squeeze(a) | a.squeeze() |
备注
逻辑运算:&或| 在NumPy中是按位AND / OR,而在Matlab&和|中 是逻辑AND / OR。
优先级:NumPy的&运算符优先于<和>之类的逻辑运算符; Matlab是相反的。
MATLAB可以立即调用路径上的任何内容。
Python需要先执行“import”语句,以使特定文件中的函数可访问。
# Make all numpy available via shorter 'np' prefix
import numpy as np
# Make all matlib functions accessible at the top level via M.func()
import numpy.matlib as M
# Make some matlib functions accessible directly at the top level via, e.g. rand(3,3)
from numpy.matlib import rand,zeros,ones,empty,eye
# Define a Hermitian function
def hermitian(A, **kwargs):
return np.transpose(A,**kwargs).conj()
# Make some shortcuts for transpose,hermitian:
# np.transpose(A) --> T(A)
# hermitian(A) --> H(A)
T = np.transpose
H = hermitian
网友评论