NumPy — 创建全零、全1、空、arange 数组,array 对象类型,astype 转换数据类型,数组和标量以及数组之间的运算,NumPy 数组共享内存

本文介绍NumPy库的基础知识,包括数组操作、数据类型管理、数学统计方法、数组运算及高级功能。NumPy是Python中进行科学计算的核心库,提供了高性能的多维数组对象和丰富的函数库。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

NumPy 简介

一个用 python 实现的科学计算包。包括:

1、一个强大的 N 维数组对象 Array

2、比较成熟的(广播)函数库;

3、用于整合 C/C++Fortran 代码的工具包;

4、实用的线性代数、傅里叶变换和随机数生成函数

NumPy 特点是其 N 维数组对象 (即 ndarray)。依照标准的 NumPy 的约定,即总是使用 import numpy as np 导入 NumPy 包。

1. 创建 ndarray

使用 array 函数,它接受一切序列型的对象,然后产生一个新的含有传入数据的 NumPy 数组。

In [7]: a = [1, 2, 3.5, 0, 4]

In [8]: np.array(a)
Out[8]: array([1. , 2. , 3.5, 0. , 4. ])

嵌套序列会被转换成一个多维数组

In [9]: data = [[1,2,3,4],[5,6,7,8]]

In [10]: np.array(data)
Out[10]: 
array([[1, 2, 3, 4],
       [5, 6, 7, 8]])

除非显示地说明,np.array 会尝试为新建的这个数组推断出一个较为合适的数据类型。保存在一个特殊的 dtype 对象中。

In [6]: arr = np.array(data)

In [7]: arr.dtype
Out[7]: dtype('int32')
  • zeros: 创建指定长度的全 0 数组

  • ones: 创建指定形状的全 1 数组

  • empty: 创建一个没有任何具体值的数组

  • arange: 是 Python 内置函数 range 的数组版

In [8]: np.zeros(5)
Out[8]: array([0., 0., 0., 0., 0.])

In [9]: np.ones(5)
Out[9]: array([1., 1., 1., 1., 1.])

In [11]: np.empty((2,3))
Out[11]: 
array([[1.53153305e-316, 1.53436276e-316, 2.50013513e-315],
       [3.58787191e-316, 2.46289313e-316, 2.46289590e-316]])

In [12]: np.arange(10)
Out[12]: array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

数组创建函数

2. ndarray的数据类型

数组的数据类型 dtype 是一个特殊的对象,它含有 ndarray 将一块内存解释为特定数据类型所需的信息。

In [13]: arr1 = np.array([1,2,3], dtype=np.int32)

In [14]: arr2 = np.array([1,2,3], dtype=np.float64)

In [15]: arr1.dtype
Out[15]: dtype('int32')

In [16]: arr2.dtype
Out[16]: dtype('float64')

NumPy数据类型
数据类型

通过 ndarrayastype 方法可以显式地转化 dtype


In [19]: arr = np.array([1,2,3,4])

In [20]: arr.dtype
Out[20]: dtype('int32')

In [21]: float_arr = arr.astype(np.float64)

In [23]: float_arr.dtype
Out[23]: dtype('float64')

3. 数组和标量以及数组之间的运算

数组和标量进行计算,计算过程是直接把数组里的元素和标量逐个进行计算,需要注意的是, 乘法是对应元素相乘, 不是矩阵内积, 矩阵内积使用的是 np.dot() 函数。

In [25]: data = np.array([[1,2,3,4],[5,6,7,8]])

In [26]: data
Out[26]: 
array([[1, 2, 3, 4],
       [5, 6, 7, 8]])

In [27]: data + 10
Out[27]: 
array([[11, 12, 13, 14],
    [15, 16, 17, 18]])

In [28]: data * 3
Out[28]: 
array([[ 3,  6,  9, 12],
    [15, 18, 21, 24]])

In [29]: data * data
Out[29]: 
array([[ 1,  4,  9, 16],
       [25, 36, 49, 64]])

4. NumPy 数组共享内存

如果要独立保存,需要显式地备份。可以使用 np.may_share_memory() 函数来判断两个数组是否共享内存。

In [1]: import numpy as np

In [2]: a = np.arange(6)

In [3]: b = a[2:5]

In [4]: a
Out[4]: array([0, 1, 2, 3, 4, 5])

In [5]: b
Out[5]: array([2, 3, 4])

In [6]: b[1] = 100

In [7]: b
Out[7]: array([  2, 100,   4])

In [8]: a
Out[8]: array([  0,   1,   2, 100,   4,   5])

In [9]: np.may_share_memory(a, b)
Out[9]: True

In [10]: b = a[2:6].copy()

In [11]: b
Out[11]: array([  2, 100,   4,   5])

In [12]: b[1] = 3

In [13]: b
Out[13]: array([2, 3, 4, 5])

In [14]: a
Out[14]: array([  0,   1,   2, 100,   4,   5])

In [15]: np.may_share_memory(a, b)
Out[15]: False

4. 基本的索引和切片

4.1 一维数组

  In [29]: arr = np.arange(6)

  In [30]: arr
  Out[30]: array([0, 1, 2, 3, 4, 5])

  In [31]: arr[3]
  Out[31]: 3

  In [32]: arr[2:5]
  Out[32]: array([2, 3, 4])

  In [33]: arr[5] = 100

  In [34]: arr
  Out[34]: array([  0,   1,   2,   3,   4, 100])

4.2 二维数组

  In [35]: arr_2d = np.array([[1,2,3],[4,5,6],[7,8,9]])

  In [36]: arr_2d
  Out[36]: 
  array([[1, 2, 3],
         [4, 5, 6],
         [7, 8, 9]])

  In [37]: arr_2d[1]
  Out[37]: array([4, 5, 6])

  In [38]: arr_2d[0][2]
  Out[38]: 3
  # arr_2d[0][2] 与 arr_2d[0,2] 等价
  In [39]: arr_2d[0,2]
  Out[39]: 3

4.3 多维数组

4.4 布尔型索引

In [1]: import numpy as np

In [2]: names = np.array(['Bob','Joe','Will','Bob','Will'])

In [3]: names
Out[3]: array(['Bob', 'Joe', 'Will', 'Bob', 'Will'], dtype='|S4')

In [4]: names == 'Bob'
Out[4]: array([ True, False, False,  True, False])

4.5 花式索引

指的是利用整数数组进行索引,假如有一个 8 × 4 数组

In [5]: arr = np.empty((8,4))

In [6]: arr
Out[6]: 
array([[4.82613331e-085, 6.96747054e+252, 5.81241635e+180,
        2.30074046e-312],
       [3.09270272e-316, 3.07615034e-316, 3.09946945e-316,
        3.07835624e-316],
       [3.09945364e-316, 3.09450863e-316, 3.09946628e-316,
        3.09451140e-316],
       [3.09950739e-316, 3.07614599e-316, 3.09947893e-316,
        3.09611889e-316],
       [3.09947577e-316, 3.07312626e-316, 3.07311243e-316,
        3.07311440e-316],
       [3.09612126e-316, 3.09612363e-316, 3.07306500e-316,
        3.07307685e-316],
       [3.07308081e-316, 3.09612601e-316, 3.07307883e-316,
        3.07308476e-316],
       [3.07307488e-316, 3.07308278e-316, 3.07309069e-316,
        3.07309464e-316]])

In [7]: for i in range(8):
   ...:     arr[i] = i
   ...:     

In [8]: arr
Out[8]: 
array([[0., 0., 0., 0.],
       [1., 1., 1., 1.],
       [2., 2., 2., 2.],
       [3., 3., 3., 3.],
       [4., 4., 4., 4.],
       [5., 5., 5., 5.],
       [6., 6., 6., 6.],
       [7., 7., 7., 7.]])

为了以特定顺序选取行子集,只需传入一个用于指定顺序的整数列表或者 ndarray 即可:

In [9]: arr[[4,3,0,6]]
Out[9]: 
array([[4., 4., 4., 4.],
       [3., 3., 3., 3.],
       [0., 0., 0., 0.],
       [6., 6., 6., 6.]])
# 使用负索引将从末尾开始选取行
In [10]: arr[[-3,-5,-7]]
Out[10]: 
array([[5., 5., 5., 5.],
       [3., 3., 3., 3.],
       [1., 1., 1., 1.]])

5. 数组转置和轴对换

转置返回的是原数据的视图,不会对原数据进行任何复制操作。

In [11]: arr = np.arange(15).reshape((3,5))

In [12]: arr
Out[12]: 
array([[ 0,  1,  2,  3,  4],
       [ 5,  6,  7,  8,  9],
       [10, 11, 12, 13, 14]])

In [13]: arr.T
Out[13]: 
array([[ 0,  5, 10],
       [ 1,  6, 11],
       [ 2,  7, 12],
       [ 3,  8, 13],
       [ 4,  9, 14]])

6. 通用函数

通用函数是一种对 ndarray 中的数据执行元素级运算的函数。

  • 一元通用函数

    In [14]: arr = np.arange(0,10,2)
    
    In [15]: arr
    Out[15]: array([0, 2, 4, 6, 8])
    # 计算各元素的平方根
    In [16]: np.sqrt(arr)
    Out[16]: array([0.        , 1.41421356, 2.        , 2.44948974, 2.82842712])
    # 计算各元素的指数 e的x次方
    In [17]: np.exp(arr)
    Out[17]: 
    array([1.00000000e+00, 7.38905610e+00, 5.45981500e+01, 4.03428793e+02,
           2.98095799e+03])
    # 计算各元素的平方
    In [18]: np.square(arr)
    Out[18]: array([ 0,  4, 16, 36, 64])
    

一元通用函数

  • 二元通用函数

    In [19]: x = np.arange(0,10,2)
    
    In [20]: x
    Out[20]: array([0, 2, 4, 6, 8])
    
    In [21]: y = np.arange(5)
    
    In [22]: y
    Out[22]: array([0, 1, 2, 3, 4])
    # 计算元素级的最大值
    In [23]: np.maximum(x, y)
    Out[23]: array([0, 2, 4, 6, 8])
    

7. 将条件逻辑表述为数组运算

numpy.where 函数时三元表达式 x if condition else y 的矢量化版本。假设我们要根据 cond 中的值选取 x 和 y 的值:当 cond 中的值为 True 时,选取 x 的值,否则从 y 中选取。

In [27]: x = np.array([1,2,3,4])

In [28]: y = np.array([5,6,7,8])

In [31]: cond = np.array([True, False, True, False])

In [32]: np.where(cond,x,y)
Out[32]: array([1, 6, 3, 8])

np.where 的第二个和第三个参数不必时数组,它们都可以使标量值。在数据分析工作中,where 通常用于根据另一个数组而产生一个新的数组。

假设有一个由随机数据组成的矩阵,我们希望将所有的正值替换为 2 ,负值替换为 -2

In [37]: arr = np.random.randn(4,4)

In [38]: arr
Out[38]: 
array([[-1.28836266, -0.79154759, -0.86565217,  1.01902521],
       [ 0.68554302, -0.08614421, -0.09703502, -0.63441371],
       [-0.93730255, -1.58755928,  0.91190601, -0.36010511],
       [ 0.63881326, -0.06695277, -0.89038554, -0.181366  ]])

In [39]: np.where(arr>0, 2, -2)
Out[39]: 
array([[-2, -2, -2,  2],
       [ 2, -2, -2, -2],
       [-2, -2,  2, -2],
       [ 2, -2, -2, -2]])

In [40]: np.where(arr>0, 2, arr)
Out[40]: 
array([[-1.28836266, -0.79154759, -0.86565217,  2.        ],
       [ 2.        , -0.08614421, -0.09703502, -0.63441371],
       [-0.93730255, -1.58755928,  2.        , -0.36010511],
       [ 2.        , -0.06695277, -0.89038554, -0.181366  ]])

8. 数学和统计方法

可以通过数组上的一组数学函数对整个数组或某个轴向的数据进行统计计算,sum、mean 以及标准差 std 等聚合计算,即可以当做数组的实例方法调用,也可以当做顶级 NumPy 函数使用:

In [52]: x = np.array([[1,2,3,4],[2,4,6,8]])

In [53]: x
Out[53]: 
array([[1, 2, 3, 4],
       [2, 4, 6, 8]])

In [54]: x.sum()
Out[54]: 30
# mean 和 sum 这类函数可以接受一个 axis 参数(用于计算该轴方向上的统计值),最# 终结果是一个少一维的数组
In [55]: x.sum(axis=0)
Out[55]: array([ 3,  6,  9, 12])
# x.mean() 等价于 np.mean(x)
In [56]: x.mean()
Out[56]: 3.75

In [58]: np.mean(x)
Out[58]: 3.75

In [59]: np.sum(x)
Out[59]: 30
  
In [60]: np.cumsum(x)
Out[60]: array([ 1,  3,  6, 10, 12, 16, 22, 30])

数组统计方法

9. 用于布尔型数组的方法

在上述统计方法中,布尔值经常会被强制转换为 1 (True) 和 0 (False),因此 sum 可以用来对布尔型数组中的 True 值进行计数。

any : 用于测试数组中是否存在一个或者多个 True

all : 用于检查数组中所有值是否都是 True

 In [61]: arr = np.random.randn(5)

 In [62]: arr
 Out[62]: array([-0.39136478, -1.41933952,  0.86864979,  0.57857464, -0.87099396])

 In [63]: (arr > 0).sum()
 Out[63]: 2

 In [64]: bools = np.array([True, False, True, False, True])

 In [65]: bools.any()
 Out[65]: True

 In [66]: bools.all()
 Out[66]: False

10. 排序

 In [67]: arr = np.random.randn(2,3)

 In [68]: arr
 Out[68]: 
 array([[ 0.2112435 ,  0.02708366,  1.7135565 ],
        [ 1.65791015,  1.84424113, -1.45151054]])

 In [69]: arr.sort()

 In [70]: arr
 Out[70]: 
 array([[ 0.02708366,  0.2112435 ,  1.7135565 ],
        [-1.45151054,  1.65791015,  1.84424113]])

 In [71]: arr.sort(1)

 In [72]: arr
 Out[72]: 
 array([[ 0.02708366,  0.2112435 ,  1.7135565 ],
        [-1.45151054,  1.65791015,  1.84424113]])
 # 多维数组可以在任何一个轴向上进行排序,只需将轴编号传给 sort 即可
 In [73]: arr.sort(0)

 In [74]: arr
 Out[74]: 
 array([[-1.45151054,  0.2112435 ,  1.7135565 ],
        [ 0.02708366,  1.65791015,  1.84424113]])

11. 唯一化以及其它集合逻辑

 In [76]: data = np.array([1,2,2,3,3,4,5,5])

 In [78]: np.unique(data)
 Out[78]: array([1, 2, 3, 4, 5])
 # in1d 用于测试 [4,8] 中的元素是否存在于 data
 In [79]: np.in1d(data,[4,8])
 Out[79]: array([False, False, False, False, False,  True, False, False])

数组集合运算

12. 将数组保存到磁盘以及读取数组文件

NumPy 能够读写磁盘上的文本数据或二进制数据。

  • 二进制数据

np.save 和 np.load 是读写磁盘数组数据的两个主要函数,默认情况下,数组是以未压缩的原始二进制格式保存在扩展名为 .npy 的文件中的。

 In [87]: arr = np.arange(10)

 In [88]: np.save('some_arry', arr)

 In [90]: np.load('some_arry.npy')
 Out[90]: array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

 In [91]: b = np.array(['a','b','c','d'])

 In [92]: b
 Out[92]: array(['a', 'b', 'c', 'd'], dtype='|S1')
 # 通过 np.savez 可以将多个数组保存到一个压缩文件中,加载.npz 文件时,会得到一# # 个类似字典的对象
 In [95]: np.savez('two_arr',arr, b)

 In [96]: t = np.load('two_arr.npz')

 In [101]: t.keys()
 Out[101]: ['arr_1', 'arr_0']

 In [102]: t['arr_0']
 Out[102]: array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

 In [103]: t['arr_1']
 Out[103]: array(['a', 'b', 'c', 'd'], dtype='|S1')
  • 文本数据

    存取文本文件时使用 np.loadtxt 或者更专业的 np.genformtxt 将数据加载到普通的 NumPy数组中。后面主要使用 pandas 中的 read_csv 和 read_table 函数

13 线性代数计算

 In [104]: x = np.array([[1,2,3],[4,5,6]])

 In [105]: y = np.array([[6,23],[-1,7],[8,9]])

 In [106]: x
 Out[106]: 
 array([[1, 2, 3],
        [4, 5, 6]])

 In [107]: y
 Out[107]: 
 array([[ 6, 23],
        [-1,  7],
        [ 8,  9]])
 # 等价于 np.dot(x,y)
 In [108]: x.dot(y) 
 Out[108]: 
 array([[ 28,  64],
        [ 67, 181]])

常用的线性代数运算

14 随机数生成

 In [109]: samples = np.random.normal(size=(4,4))

 In [110]: samples
 Out[110]: 
 array([[ 1.41219058e-01, -2.61687462e-01, -2.06544530e-01,
          5.57678964e-01],
        [ 2.32015368e+00, -1.21798230e+00, -1.71956114e-01,
          1.16218074e+00],
        [ 1.18028454e-05,  9.53225142e-01, -1.80567054e-01,
          4.87805927e-01],
        [-1.96884788e-01, -2.16054931e-01, -1.02006931e-01,
          1.98486048e-01]])
 ```

![随机函数](https://img-blog.csdnimg.cn/20190608151608310.jpg?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dvaHUxMTA0,size_16,color_FFFFFF,t_70)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

wohu007

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值