参考链接: Python中的numpy.logaddexp2
part(三)
Numpy 使用教程--Numpy 数组操作及随机抽样
一、实验介绍
1.1 实验内容
如果你使用 Python 语言进行科学计算,那么一定会接触到 Numpy。Numpy 是支持 Python 语言的数值计算扩充库,其拥有强大的高维度数组处理与矩阵运算能力。除此之外,Numpy 还内建了大量的函数,方便你快速构建数学模型。
1.2 实验知识点
Numpy 数组的基本操作
1.3 实验环境
python2.7Xfce 终端ipython 终端
1.4 适合人群
本课程难度为一般,属于初级级别课程,适合具有 Python 基础,并对使用 Numpy 进行科学计算感兴趣的用户。
二、Numpy 数组的基本操作
上一个章节,我们了解了如何利用 numpy 创建各式各样的 ndarray。本章节,我们将利用学会针对 ndarray 的各种花式操作技巧。
2.1 重设形状
reshape 可以在不改变数组数据的同时,改变数组的形状。其中,numpy.reshape() 等效于 ndarray.reshape()。reshape 方法非常简单:
numpy.reshape(a, newshape)
其中,a 表示原数组,newshape 用于指定新的形状(整数或者元组)。
举个例子:
import numpy as np
np.arange(10).reshape((5, 2))
2.2 数组展开
ravel 的目的是将任意形状的数组扁平化,变为 1 维数组。ravel 方法如下:
numpy.ravel(a, order='C')
其中,a 表示需要处理的数组。order 表示变换时的读取顺序,默认是按照行依次读取,当 order='F' 时,可以按列依次读取排序。
示例:
import numpy as np
a = np.arange(10).reshape((2, 5))
np.ravel(a)
np.ravel(a, order='F')
2.3 轴移动
moveaxis 可以将数组的轴移动到新的位置。其方法如下:
numpy.moveaxis(a, source, destination)
其中:
a:数组。source:要移动的轴的原始位置。destination:要移动的轴的目标位置。
举个例子:
import numpy as np
a = np.ones((1, 2, 3))
np.moveaxis(a, 0, -1)
你可能没有看明白是什么意思,我们可以输出二者的 shape属性:
2.4 轴交换
和 moveaxis 不同的是,swapaxes 可以用来交换数组的轴。其方法如下:
numpy.swapaxes(a, axis1, axis2)
其中:
a:数组。axis1:需要交换的轴 1 位置。axis2:需要与轴 1 交换位置的轴 1 位置。
举个例子:
import numpy as np
a = np.ones((1, 4, 3))
np.swapaxes(a, 0, 2)
我们直接输出两个数组的 shape 值。
2.5 数组转置
transpose 类似于矩阵的转置,它可以将 2 维数组的横轴和纵轴交换。其方法如下:
numpy.transpose(a, axes=None)
其中:
a:数组。axis:该值默认为 none,表示转置。如果有值,那么则按照值替换轴。
举个例子:
import numpy as np
a = np.arange(4).reshape(2,2)
np.transpose(a)
2.6 维度改变
atleast_xd 支持将输入数据直接视为 x维。这里的 x 可以表示:1,2,3。方法分别维:
numpy.atleast_1d()
numpy.atleast_2d()
numpy.atleast_3d()
举个例子:
import numpy as np
np.atleast_1d([1])
np.atleast_2d([1])
np.atleast_3d([1])
2.7 类型转变
在 numpy 中,还有一系列以 as 开头的方法,它们可以将特定输入转换为数组,亦可将数组转换为矩阵、标量,ndarray 等。如下:
asarray(a,dtype,order):将特定输入转换为数组。asanyarray(a,dtype,order):将特定输入转换为 ndarray。asmatrix(data,dtype):将特定输入转换为矩阵。asfarray(a,dtype):将特定输入转换为 float 类型的数组。asarray_chkfinite(a,dtype,order):将特定输入转换为数组,检查 NaN 或 infs。asscalar(a):将大小为 1 的数组转换为标量。
这里以 asmatrix(data,dtype) 方法举例:
import numpy as np
a = np.arange(4).reshape(2,2)
np.asmatrix(a)
2.8 数组连接
concatenate 可以将多个数组沿指定轴连接在一起。其方法为:
numpy.concatenate((a1, a2, ...), axis=0)
其中:
(a1, a2, ...):需要连接的数组。axis:指定连接轴。
举个例子:
import numpy as np
a = np.array([[1, 2], [3, 4], [5, 6]])
b = np.array([[7, 8], [9, 10]])
c = np.array([[11, 12]])
np.concatenate((a, b, c), axis=0)
这里,我们可以尝试沿着横轴连接。但要保证连接处的维数一致,所以这里用到了 .T 转置。
a = np.array([[1, 2], [3, 4], [5, 6]])
b = np.array([[7, 8, 9]])
np.concatenate((a, b.T), axis=1)
2.9 数组堆叠
在 numpy 中,还有一系列以 as 开头的方法,它们可以将特定输入转换为数组,亦可将数组转换为矩阵、标量,ndarray 等。如下:
stack(arrays,axis):沿着新轴连接数组的序列。column_stack():将 1 维数组作为列堆叠到 2 维数组中。hstack():按水平方向堆叠数组。vstack():按垂直方向堆叠数组。dstack():按深度方向堆叠数组。
这里以 stack(arrays,axis) 方法举例:
import numpy as np
a = np.array([1, 2, 3])
b = np.array([4, 5, 6])
np.stack((a, b))
当然,也可以横着堆叠。
np.stack((a, b), axis=-1)
2.10 拆分
split 及与之相似的一系列方法主要是用于数组的拆分,列举如下:
split(ary,indices_or_sections,axis):将数组拆分为多个子数组。dsplit(ary,indices_or_sections):按深度方向将数组拆分成多个子数组。hsplit(ary,indices_or_sections):按水平方向将数组拆分成多个子数组。vsplit(ary,indices_or_sections):按垂直方向将数组拆分成多个子数组。
下面,我们看一看 split 到底有什么效果:
import numpy as np
a = np.arange(10)
np.split(a, 5)
除了 1 维数组,更高维度也是可以直接拆分的。例如,我们可以将下面的数组按行拆分为 2。
import numpy as np
a = np.arange(10).reshape(2,5)
np.split(a, 2)
numpy 中还有针对数组元素添加或移除的一些方法。
2.11 删除
delete(arr,obj,axis):沿特定轴删除数组中的子数组。
下面,依次对 4 种方法进行示例,首先是 delete 删除:
import numpy as np
a = np.arange(12).reshape(3,4)
np.delete(a, 2, 1)
这里代表沿着横轴,将第 3 列(索引 2)删除。
当然,你也可以沿着纵轴,将第三行删除。
np.delete(a, 2, 0)
2.12 数组插入
insert(arr,obj,values,axis):依据索引在特定轴之前插入值。
再看一看 insert插入, 用法和 delete 很相似,只是需要在第三个参数位置设置需要插入的数组对象:
import numpy as np
a = np.arange(12).reshape(3,4)
b = np.arange(4)
np.insert(a, 2, b, 0)
2.13 附加
append(arr,values,axis):将值附加到数组的末尾,并返回 1 维数组。
append 的用法也非常简单。只需要设置好需要附加的值和轴位置就好了。它其实相当于只能在末尾插入的 insert,所以少了一个指定索引的参数。
import numpy as np
a = np.arange(6).reshape(2,3)
b = np.arange(3)
np.append(a, b)
注意 append方法返回值,默认是展平状态下的 1 维数组。
2.14 重设尺寸
resize(a,new_shape):对数组尺寸进行重新设定。
resize 就很好理解了,直接举例子吧:
import numpy as np
a = np.arange(10)
a.resize(2,5)
你可能会纳闷了,这个 resize 看起来和上面的 reshape 一样呢,都是改变数组原有的形状。
其实,它们直接是有区别的,区别在于对原数组的影响。reshape 在改变形状时,不会影响原数组,相当于对原数组做了一份拷贝。而 resize 则是对原数组执行操作。
2.15 翻转数组
在 numpy 中,我们还可以对数组进行翻转操作:
fliplr(m):左右翻转数组。flipud(m):上下翻转数组。
举个例子:
import numpy as np
a = np.arange(16).reshape(4,4)
n.fliplr(a)
n.flipud(a)
三、Numpy 随机抽样
Numpy 的随机抽样功能非常强大,主要由 numpy.random 模块完成。
首先,我们需要了解如何使用 numpy 也就是生成一些满足基本需求的随机数据。主要由以下一些方法完成:
3.1 numpy.random.rand
numpy.random.rand(d0, d1, ..., dn) 方法的作用为:指定一个数组,并使用 [0, 1) 区间随机数据填充,这些数据均匀分布。
import numpy as np
np.random.rand(2,5)
3.2 numpy.random.randn
numpy.random.randn(d0, d1, ..., dn) 与 numpy.random.rand(d0, d1, ..., dn) 的区别在于,返回的随机数据符合标准正太分布。
import numpy as np
np.random.randn(1,10)
3.3 numpy.random.randint
randint(low, high, size, dtype) 方法将会生成 [low, high) 的随机整数。注意这是一个半开半闭区间。
import numpy as np
np.random.randint(2,5,10)
3.4 numpy.random.random_integers
random_integers(low, high, size) 方法将会生成 [low, high] 的 np.int 类型随机整数。注意这是一个闭区间。
import numpy as np
np.random.random_integers(2,5,10)
3.5 numpy.random.random_sample
random_sample(size) 方法将会在 [0, 1) 区间内生成指定 size 的随机浮点数。
import numpy as np
np.random.random_sample([10])
与 numpy.random.random_sample 类似的方法还有:
numpy.random.random([size])numpy.random.ranf([size])numpy.random.sample([size])
它们 4 个的效果都差不多。
3.6 numpy.random.choice
choice(a, size, replace, p) 方法将会给定的 1 维数组里生成随机数。
import numpy as np
np.random.choice(10,5)
上面的代码将会在 np.arange(10) 中生成 5 个随机数。
3.7 概率密度分布
除了上面介绍的 6 中随机数生成方法,numpy 还提供了大量的满足特定概率密度分布的样本生成方法。它们的使用方法和上面非常相似,这里就不再一一介绍了。列举如下:
numpy.random.beta(a,b,size):从 Beta 分布中生成随机数。numpy.random.binomial(n, p, size):从二项分布中生成随机数。numpy.random.chisquare(df,size):从卡方分布中生成随机数。numpy.random.dirichlet(alpha,size):从 Dirichlet 分布中生成随机数。numpy.random.exponential(scale,size):从指数分布中生成随机数。numpy.random.f(dfnum,dfden,size):从 F 分布中生成随机数。numpy.random.gamma(shape,scale,size):从 Gamma 分布中生成随机数。numpy.random.geometric(p,size):从几何分布中生成随机数。numpy.random.gumbel(loc,scale,size):从 Gumbel 分布中生成随机数。numpy.random.hypergeometric(ngood, nbad, nsample, size):从超几何分布中生成随机数。numpy.random.laplace(loc,scale,size):从拉普拉斯双指数分布中生成随机数。numpy.random.logistic(loc,scale,size):从逻辑分布中生成随机数。numpy.random.lognormal(mean,sigma,size):从对数正态分布中生成随机数。numpy.random.logseries(p,size):从对数系列分布中生成随机数。numpy.random.multinomial(n,pvals,size):从多项分布中生成随机数。numpy.random.multivariate_normal(mean, cov, size):从多变量正态分布绘制随机样本。numpy.random.negative_binomial(n, p, size):从负二项分布中生成随机数。numpy.random.noncentral_chisquare(df,nonc,size):从非中心卡方分布中生成随机数。numpy.random.noncentral_f(dfnum, dfden, nonc, size):从非中心 F 分布中抽取样本。numpy.random.normal(loc,scale,size):从正态分布绘制随机样本。numpy.random.pareto(a,size):从具有指定形状的 Pareto II 或 Lomax 分布中生成随机数。numpy.random.poisson(lam,size):从泊松分布中生成随机数。numpy.random.power(a,size):从具有正指数 a-1 的功率分布中在 0,1 中生成随机数。numpy.random.rayleigh(scale,size):从瑞利分布中生成随机数。numpy.random.standard_cauchy(size):从标准 Cauchy 分布中生成随机数。numpy.random.standard_exponential(size):从标准指数分布中生成随机数。numpy.random.standard_gamma(shape,size):从标准 Gamma 分布中生成随机数。numpy.random.standard_normal(size):从标准正态分布中生成随机数。numpy.random.standard_t(df,size):从具有 df 自由度的标准学生 t 分布中生成随机数。numpy.random.triangular(left,mode,right,size):从三角分布中生成随机数。numpy.random.uniform(low,high,size):从均匀分布中生成随机数。numpy.random.vonmises(mu,kappa,size):从 von Mises 分布中生成随机数。numpy.random.wald(mean,scale,size):从 Wald 或反高斯分布中生成随机数。numpy.random.weibull(a,size):从威布尔分布中生成随机数。numpy.random.zipf(a,size):从 Zipf 分布中生成随机数。
四、实验总结
本章节介绍了针对 Ndarray 的常用操作,并了解了 Numpy.randon 类下的随机抽样方法。这两点内容都非常重要,也非常实用。由于随机抽样的方法太多,全部记忆下来不太实际,你可以多浏览几遍留下印象,需要时再查阅官方文档。
part(四)
Numpy 使用教程--Numpy 数学函数及代数运算
一、实验介绍
1.1 实验内容
如果你使用 Python 语言进行科学计算,那么一定会接触到 Numpy。Numpy 是支持 Python 语言的数值计算扩充库,其拥有强大的高维度数组处理与矩阵运算能力。除此之外,Numpy 还内建了大量的函数,方便你快速构建数学模型。
1.2 实验知识点
Numpy 数学函数Numpy 代数运算
1.3 实验环境
python2.7Xfce 终端ipython 终端
1.4 适合人群
本课程难度为一般,属于初级级别课程,适合具有 Python 基础,并对使用 Numpy 进行科学计算感兴趣的用户。
二、数学函数
使用 python 自带的运算符,你可以完成数学中的加减乘除,以及取余、取整,幂次计算等。导入自带的 math 模块之后,里面又包含绝对值、阶乘、开平方等一些常用的数学函数。不过,这些函数仍然相对基础。如果要完成更加复杂一些的数学计算,就会显得捉襟见肘了。
numpy 为我们提供了更多的数学函数,以帮助我们更好地完成一些数值计算。下面就依次来看一看。
2.1 三角函数
首先, 看一看 numpy 提供的三角函数功能。这些方法有:
numpy.sin(x):三角正弦。numpy.cos(x):三角余弦。numpy.tan(x):三角正切。numpy.arcsin(x):三角反正弦。numpy.arccos(x):三角反余弦。numpy.arctan(x):三角反正切。numpy.hypot(x1,x2):直角三角形求斜边。numpy.degrees(x):弧度转换为度。numpy.radians(x):度转换为弧度。numpy.deg2rad(x):度转换为弧度。numpy.rad2deg(x):弧度转换为度。
比如,我们可以用上面提到的 numpy.rad2deg(x) 将弧度转换为度。
import numpy as np
np.rad2deg(np.pi)
这些函数非常简单,就不再一一举例了。
2.2 双曲函数
在数学中,双曲函数是一类与常见的三角函数类似的函数。双曲函数经常出现于某些重要的线性微分方程的解中,使用 numpy 计算它们的方法为:
numpy.sinh(x):双曲正弦。numpy.cosh(x):双曲余弦。numpy.tanh(x):双曲正切。numpy.arcsinh(x):反双曲正弦。numpy.arccosh(x):反双曲余弦。numpy.arctanh(x):反双曲正切。
2.3 数值修约
数值修约, 又称数字修约, 是指在进行具体的数字运算前, 按照一定的规则确定一致的位数, 然后舍去某些数字后面多余的尾数的过程[via. 维基百科]。比如, 我们常听到的「4 舍 5 入」就属于数值修约中的一种。
numpy.around(a):平均到给定的小数位数。numpy.round_(a):将数组舍入到给定的小数位数。numpy.rint(x):修约到最接近的整数。numpy.fix(x, y):向 0 舍入到最接近的整数。numpy.floor(x):返回输入的底部(标量 x 的底部是最大的整数 i)。numpy.ceil(x):返回输入的上限(标量 x 的底部是最小的整数 i).numpy.trunc(x):返回输入的截断值。
随机选择几个浮点数,看一看上面方法的区别。
>>> import numpy as np
>>> a = np.array([1.21, 2.53, 3.86])
>>> a
array([ 1.21, 2.53, 3.86])
>>> np.around(a)
array([ 1., 3., 4.])
>>> np.round_(a)
array([ 1., 3., 4.])
>>> np.rint(a)
array([ 1., 3., 4.])
>>> np.fix(a)
array([ 1., 2., 3.])
>>> np.floor(a)
array([ 1., 2., 3.])
>>> np.ceil(a)
array([ 2., 3., 4.])
>>> np.trunc(a)
array([ 1., 2., 3.])
2.4 求和、求积、差分
下面这些方法用于数组内元素或数组间进行求和、求积以及进行差分。
numpy.prod(a, axis, dtype, keepdims):返回指定轴上的数组元素的乘积。numpy.sum(a, axis, dtype, keepdims):返回指定轴上的数组元素的总和。numpy.nanprod(a, axis, dtype, keepdims):返回指定轴上的数组元素的乘积, 将 NaN 视作 1。numpy.nansum(a, axis, dtype, keepdims):返回指定轴上的数组元素的总和, 将 NaN 视作 0。numpy.cumprod(a, axis, dtype):返回沿给定轴的元素的累积乘积。numpy.cumsum(a, axis, dtype):返回沿给定轴的元素的累积总和。numpy.nancumprod(a, axis, dtype):返回沿给定轴的元素的累积乘积, 将 NaN 视作 1。numpy.nancumsum(a, axis, dtype):返回沿给定轴的元素的累积总和, 将 NaN 视作 0。numpy.diff(a, n, axis):计算沿指定轴的第 n 个离散差分。numpy.ediff1d(ary, to_end, to_begin):数组的连续元素之间的差异。numpy.gradient(f):返回 N 维数组的梯度。numpy.cross(a, b, axisa, axisb, axisc, axis):返回两个(数组)向量的叉积。numpy.trapz(y, x, dx, axis):使用复合梯形规则沿给定轴积分。
下面,我们选取几个举例测试一下:
>>> import numpy as np
>>> a=np.arange(5)
>>> a
array([0, 1, 2, 3, 4])
>>> np.prod(a) # 所有元素乘积
0
>>> np.sum(a) # 所有元素和
10
>>> np.nanprod(a) # 默认轴上所有元素乘积
0
>>> np.nansum(a) # 默认轴上所有元素和
10
>>> np.cumprod(a) # 默认轴上元素的累积乘积。
array([0, 0, 0, 0, 0])
>>> np.diff(a) # 默认轴上元素差分。
array([1, 1, 1, 1])
2.5 指数和对数
如果你需要进行指数或者对数求解,可以用到以下这些方法。
numpy.exp(x):计算输入数组中所有元素的指数。numpy.expm1(x):对数组中的所有元素计算 exp(x) - 1.numpy.exp2(x):对于输入数组中的所有 p, 计算 2 ** p。numpy.log(x):计算自然对数。numpy.log10(x):计算常用对数。numpy.log2(x):计算二进制对数。numpy.log1p(x):log(1 x)。numpy.logaddexp(x1, x2):log2(2**x1 2**x2)。numpy.logaddexp2(x1, x2):log(exp(x1) exp(x2))。
2.6 算术运算
当然,numpy 也提供了一些用于算术运算的方法,使用起来会比 python 提供的运算符灵活一些,主要是可以直接针对数组。
numpy.add(x1, x2):对应元素相加。numpy.reciprocal(x):求倒数 1/x。numpy.negative(x):求对应负数。numpy.multiply(x1, x2):求解乘法。numpy.divide(x1, x2):相除 x1/x2。numpy.power(x1, x2):类似于 x1^x2。numpy.subtract(x1, x2):减法。numpy.fmod(x1, x2):返回除法的元素余项。numpy.mod(x1, x2):返回余项。numpy.modf(x1):返回数组的小数和整数部分。numpy.remainder(x1, x2):返回除法余数。
>>> import numpy as np
>>> a1 = np.random.randint(0, 10, 5)
>>> a2 = np.random.randint(0, 10, 5)
>>> a1
array([3, 7, 8, 0, 0])
>>> a2
array([1, 8, 6, 4, 4])
>>> np.add(a1, a2)
array([ 4, 15, 14, 4, 4])
>>> np.reciprocal(a1)
array([0, 0, 0, , ])
>>> np.negative(a1)
array([-3, -7, -8, 0, 0])
>>> np.multiply(a1, a2)
array([ 3, 56, 48, 0, 0])
>>> np.divide(a1, a2)
array([3, 0, 1, 0, 0])
>>> np.power(a1, a2)
array([3,5764801,262144,0,0])
>>> np.subtract(a1, a2)
array([ 2, -1, 2, -4, -4])
>>> np.fmod(a1, a2)
array([0, 7, 2, 0, 0])
>>> np.mod(a1, a2)
array([0, 7, 2, 0, 0])
>>> np.modf(a1)
(array([ 0., 0., 0., 0., 0.]), array([ 3., 7., 8., 0., 0.]))
>>> np.remainder(a1, a2)
array([0, 7, 2, 0, 0])
>>>
2.7 矩阵和向量积
求解向量、矩阵、张量的点积等同样是 numpy 非常强大的地方。
numpy.dot(a,b):求解两个数组的点积。numpy.vdot(a,b):求解两个向量的点积。numpy.inner(a,b):求解两个数组的内积。numpy.outer(a,b):求解两个向量的外积。numpy.matmul(a,b):求解两个数组的矩阵乘积。numpy.tensordot(a,b):求解张量点积。numpy.kron(a,b):计算 Kronecker 乘积。
2.8 其他
除了上面这些归好类别的方法,numpy 中还有一些用于数学运算的方法,归纳如下:
numpy.angle(z, deg):返回复参数的角度。numpy.real(val):返回数组元素的实部。numpy.imag(val):返回数组元素的虚部。numpy.conj(x):按元素方式返回共轭复数。numpy.convolve(a, v, mode):返回线性卷积。numpy.sqrt(x):平方根。numpy.cbrt(x):立方根。numpy.square(x):平方。numpy.absolute(x):绝对值, 可求解复数。numpy.fabs(x):绝对值。numpy.sign(x):符号函数。numpy.maximum(x1, x2):最大值。numpy.minimum(x1, x2):最小值。numpy.nan_to_num(x):用 0 替换 NaN。numpy.interp(x, xp, fp, left, right, period):线性插值。
三、代数运算
上面,我们分为 8 个类别,介绍了 numpy 中常用到的数学函数。这些方法让复杂的计算过程表达更为简单。除此之外,numpy 中还包含一些代数运算的方法,尤其是涉及到矩阵的计算方法,求解特征值、特征向量、逆矩阵等,非常方便。
numpy.linalg.cholesky(a):Cholesky 分解。numpy.linalg.qr(a ,mode):计算矩阵的 QR 因式分解。numpy.linalg.svd(a ,full_matrices,compute_uv):奇异值分解。numpy.linalg.eig(a):计算正方形数组的特征值和右特征向量。numpy.linalg.eigh(a, UPLO):返回 Hermitian 或对称矩阵的特征值和特征向量。numpy.linalg.eigvals(a):计算矩阵的特征值。numpy.linalg.eigvalsh(a, UPLO):计算 Hermitian 或真实对称矩阵的特征值。numpy.linalg.norm(x ,ord,axis,keepdims):计算矩阵或向量范数。numpy.linalg.cond(x ,p):计算矩阵的条件数。numpy.linalg.det(a):计算数组的行列式。numpy.linalg.matrix_rank(M ,tol):使用奇异值分解方法返回秩。numpy.linalg.slogdet(a):计算数组的行列式的符号和自然对数。numpy.trace(a ,offset,axis1,axis2,dtype,out):沿数组的对角线返回总和。numpy.linalg.solve(a,b):求解线性矩阵方程或线性标量方程组。numpy.linalg.tensorsolve(a,b ,axes):为 x 解出张量方程a x = bnumpy.linalg.lstsq(a,b ,rcond):将最小二乘解返回到线性矩阵方程。numpy.linalg.inv(a):计算逆矩阵。numpy.linalg.pinv(a ,rcond):计算矩阵的(Moore-Penrose)伪逆。numpy.linalg.tensorinv(a ,ind):计算N维数组的逆。
四、实验总结
数学函数和代数运算方法是使用 numpy 进行数值计算中的利器,numpy 针对矩阵的高效率处理,往往可以达到事半功倍的效果。