001.数据分析_NumPy模块详解

无奋斗不青春

我 的 个 人 主 页:👉👉 失心疯的个人主页 👈👈
入 门 教 程 推 荐 :👉👉 Python零基础入门教程合集 👈👈
虚 拟 环 境 搭 建 :👉👉 Python项目虚拟环境(超详细讲解) 👈👈
PyQt5 系 列 教 程:👉👉 Python GUI(PyQt5)文章合集 👈👈
Oracle数据库教程:👉👉 Oracle数据库文章合集 👈👈
优 质 资 源 下 载 :👉👉 资源下载合集 👈👈
优 质 教 程 推 荐:👉👉 Python爬虫从入门到入狱系列 合集👈👈

分隔线

  • numpy:基础数值算法
  • scipy:科学计数
  • matplotlib:数据可视化
  • pandas:序列高级函数

NumPy

  • 官方文档:https://numpy.org/devdocs/index.html

概念

  • NumPy 的全称是“ Numeric Python”,它是Python的第三方扩展包,主要用来计算、处理一维或多维数组。
  • Numpy是其他数据分析及机器学习库的底层库,完全标准C语言实现,运行效率充分优化。
  • Numpy开源免费
  • 在数组算术计算方面, NumPy提供了大量的数学函数。NumPy的底层主要用C语言编写,因此它能够高速地执行数值计算。
  • NumPy还提供了多种数据结构,这些数据结构能够非常契合的应用在数组和矩阵的运算上随着数据科学(Data Science,简称DS,包括大数据分析与处理、大数据存储、数据抓取等分支)的蓬勃发展,像 NumPy、SciPy(Python科学计算库)、Pandas(基于NumPy的数据处理库) 等数据分析库都有了大量的增长,它们都具有较简单的语法格式。
  • 在矩阵乘法与数组形状处理上,NumPy有着非常不错的性能,再加上NumPy的计算速度很快,这些都是NumPy成为一款数据分析工具的重要原因。
  • 数组形状可以理解为数组的维度,比如一维数组、二维数组、三维数组等;以二维数组为例,改变数组形状就是交换数组的行和列,也即将数组旋转90度
  • 使用Numpy可以方便的使用数组、矩阵进行计算,包含:线性代数、傅里叶变换、随机数生成等大量函数

Numpy的核心:多维数组

  • 代码简洁:减少Python代码中的循环
  • 底层实现:厚内核(C)+ 薄接口(Python),保证性能
为什么使用Numpy
  • 对于同样的数值计算任务,使用Numpy与直接用Python代码实现对比
    • 代码更简洁:Numpy直接以数组、矩阵为粒度计算并支撑大量的数学函数,而python代码需要用for循环从底层实现
    • 性能高效:Numpy的数组存储效率和输入输出计算性能,比Python使用List或者嵌套List好很多
      • 注:Numpy的数据存储和Python原生的List是不一样的
      • 注:Numpy的大部分代码都是C语言实现,这使得Numpy比纯Python代码更高效
  • Numpy是Python各种数据科学类库的基础库
    • 比如:Scipy、Scikit-Learn、TensorFlow、pandas等
Numpy与纯Python代码实现对比
  • 需求:
    • 实现两个数组的元素相加
    • 数组A是0到N-1数字的平方 [0, 1, 4, 9, …]
    • 数组B是0到N-1数字的立方 [0, 1, 8, 27, …]
  • 需求实现
    • 纯Python代码实现
      # 定义一个方法,对两个数组的元素进行相加
      def python_sum(n):
          # 使用列表生成式创建数组A:0到N-1的平方
          a = [i ** 2 for i in range(n)]
          # 使用列表生成式创建数组B:0到N-1的立方
          b = [i ** 3 for i in range(n)]
      
          # 定义一个新列表,用于存储结果
          sum_result = []
      
          # 通过循环,将两个数组的元素进行相加,并赋值到结果列表中
          for i in range(len(a)):
              sum_result.append(a[i]+b[i])
      
          # 返回结算结果
          return sum_result
      
      # 调用方法,进行计算
      print(python_sum(10))
      
      # 输出结果
      [0, 2, 12, 36, 80, 150, 252, 392, 576, 810]
      
    • Numpy实现
      def numpy_sum(n):
          # 使用numpy的arange()方法生成数组A
          a = np.arange(n) ** 2
          # 使用numpy的arange()方法生成数组B
          b = np.arange(n) ** 3
          # numpy中两个数组直接相加
          return a + b
      
      print(numpy_sum(10))
      
      # 输出结果:
      [  0   2  12  36  80 150 252 392 576 810]
      
    • 运行时间
      import time
      
      stattime1 = time.time()
      python_sum(10000000)
      print('python_sum:', time.time() - stattime1)
      
      stattime2 = time.time()
      numpy_sum(10000000)
      print(' numpy_sum:', time.time() - stattime2)
      
      # 输出结果
      python_sum: 7.6196465492248535
       numpy_sum: 0.07576680183410645
      
  • 对比结果
    • 从代码量方面来看,使用numpy实现比纯Python代码实现更简洁
    • 从运行时间方面来看,使用numpy实现比纯Python代码实现效率更高

NumPy下载与安装

  • NumPy是Python的第三方扩展包,因此需要单独安装它
    pip install numpy
    
  • 在实际项目中,NumPy通常与SciPy程序包一起使用,SciPy 可以看做对NumPy库的扩展,它在NumPy的基础上又增加了许多工程计算函数。因此将它们同时安装是一个不错的选择。
  • 这里只是针对NumPy进行学习,可以不用考虑SciPy的安装方法
  • 注意:在Windows下直接使用pip安装SciPy会发生报错,需要我们解决SciPy的依赖项问题

ndarray对象

概念
  • NumPy定义了一个n维数组对象,简称ndarray对象,它是一个一系列相同类型元素组成的数组集合。数组中的每个元素都占有大小相同的内存块

  • ndarray对象采用了数组的索引机制,将数组中的每个元素映射到内存块上,并且按照一定的布局对内存块进行排列(行或列)

    • 在这里插入图片描述
  • ndarray中的每个元素是数据类型对象的对象(称为 dtype)。

  • 从ndarray对象通过切片提取的任何元素,都是由一个数组标量类型的Python对象表示

创建
常用方法
  • 语法
    # 创建普通数组
    numpy.array(object, dtype = None, copy = True, order = None, subok = False, ndmin = 0)
    
    # 创建区间数组
    numpy.arange(start, stop, step, dtype)
    
    # 创建等差数列数组
    numpy.linspace(start, stop, num=50, endpoint=True, retstep=False, dtype=None, axis=0)
    
    # 创建等比数列数组
    numpy.logspace(start, stop, num=50, endpoint=True, base=10.0, dtype=None, axis=0)
    
    # 创建全0数列数组
    numpy.zeros(shape, dtype=None, order='C', *args, **kwargs)
    
    # 创建全1数列数组
    numpy.ones(shape, dtype=None, order='C', *args, **kwargs)
    
创建普通数组
  • 语法
    numpy.array(object, dtype = None, copy = True, order = None, subok = False, ndmin = 0)
    
    # 参数说明
    # object    # 用于创建数组的一个数组序列
    # dtype     # 可选参数,通过它可以更改数组的数据类型
    # copy      # 可选参数,默认是True
        # 当通过ndarray数组创建新数组时,是否复制这个数组到新的内存
    # order     # 可选参数,创建数组的内存布局模式
        # C     # 行序列
        # F     # 列序列
        # A     # 默认,任意
    # subok     # 可选参数,默认是False,设置返回对象的类型
        # 为True,使用数据源object的内部数据类型
        # 为False,使用数组的数据类型
    # ndim      # 可选参数,用于指定返回数组的维数
    
  • 创建数组,不带参数
  • 创建一维数组
    import numpy as np
    
    arr1 = np.array(['a', 'b', 'c'])                # 列表
    arr2 = np.array(('d', 'e', 'f'))                # 元组
    arr3 = np.array(range(10))                      # 迭代对象
    arr4 = np.array([i ** 2 for i in range(10)])    # 生成器
    
    print(arr1)     # --> ['a' 'b' 'c']
    print(arr2)     # --> ['d' 'e' 'f']
    print(arr3)     # --> [0 1 2 3 4 5 6 7 8 9]
    print(arr4)     # --> [ 0  1  4  9 16 25 36 49 64 81]
    
    # 创建10以内的偶数数组
    arr = np.array([i for i in range(10) if i%2==0])
    
    print(arr)      # --> [0 2 4 6 8]
    
    # 列表中元素类型不相同
    arr = np.array([1, 2, 3, 4, '5'])
    
    print(arr)      # --> ['1' '2' '3' '4' '5']
    # 数组是一系列相同类型元素,当列表中元素类型不相同时
    # 元素中哪种数据类型占用存储内存最大,就以哪种数据类型存储所有元素
    
  • 创建多维数组
    arr2 = np.array([[1, 2, 3],[4, 5, 6]])
    print(arr2)
    
    # ---> 输出结果
    [[1 2 3]
     [4 5 6]]
     
    # 嵌套序列元素个数不一致
    arr = np.array([[1, 2, 3], ['a', 'b', 'c', 'd']])
    print(arr)
    
    # 报错!
        setting an array element with a sequence. 
        The requested array has an inhomogeneous shape after 1 dimensions. 
        The detected shape was (2,) + inhomogeneous part.
    
  • 创建数组,设置dtype参数
    # 将整型数据设置成浮点型
    arr = np.array([1, 2, 3, 4, 5], dtype='float')
    print(arr)      # --> [1. 2. 3. 4. 5.]
    
    # 将浮点型数据设置成整型
    arr = np.array([1.1, 2.5, 3.8, 4.3, 5], dtype='int')
    print(arr)      # [1 2 3 4 5]
    # python默认取整不会进行四舍五入
    # 如果需要四舍五入,则需要用round()函数
    
  • 创建数组,设置copy参数
    • 首先复习一下python基础中的变量赋值操作
    a = [1, 3, 5]
    # 列表[1, 3, 5]存储在内存中,变量a引用这个内存地址(可以理解为变量a中存储这个内存地址)
    b = a
    # 变量b引用变量a引用的内存地址(可以理解为变量b中也存储变量a中存储的内存地址)
    
    print('a:', a)     # --> a: [1, 3, 5]
    print('b:', b)     # --> b: [1, 3, 5]
    
    b[1] = 10
    print('a:', a)     # --> a: [1, 10, 5]
    print('b:', b)     # --> b: [1, 10, 5]
    
    # 从结果可以看到,列表a和列表b的第二个元素都改变了
    # 原因:
        # b[1] = 10操作,实际是修改了b引用的内存地址中存储的列表
        # 而列表a也是引用的这个内存地址,所以列表a也会发生变化
    
    • numpy的数组赋值与python变量赋值相似
    arr = np.array([1, 2, 3, 4])
    brr = arr
    print('arr:', arr)      # --> arr: [1 2 3 4]
    print('brr:', brr)      # --> brr: [1 2 3 4]
    
    brr[1] = 20
    
    print('arr:', arr)      # --> arr: [ 1 20  3  4]
    print('brr:', brr)      # --> brr: [ 1 20  3  4]
    
    # 修改数组brr的元素时,数组arr也会发生改变
    
    # 为了避免这种情况,可以通过数组arr重新创建一个数组brr
    arr = np.array([1, 2, 3, 4])
    brr = np.array(arr)
    print('arr:', arr)      # --> arr: [1 2 3 4]
    print('brr:', brr)      # --> brr: [1 2 3 4]
    
    brr[1] = 20
    
    print('arr:', arr)      # --> arr: [1 2 3 4]
    print('brr:', brr)      # --> brr: [ 1 20  3  4]
    
    • copy参数为True
    arr = np.array([1, 2, 3, 4])
    
    # copy参数为True,复制一个arr数组到内存中
    brr = np.array(arr, copy=True)
    
    print('arr:', id(arr))     # --> arr: 2082990288400
    print('brr:', id(brr))     # --> brr: 2082990288592
    # 复制了一个数组到新的内存,所以内存地址不一致
    
    brr[1] = 25
    
    print('arr:', arr)      # --> arr:[ 1 2  3  4]
    print('brr:', brr)      # --> brr:[ 1 25  3  4]
    
    • copy参数为False
    arr = np.array([1, 2, 3, 4])
    
    # copy参数为True,复制一个arr数组到内存中
    brr = np.array(arr, copy=False)
    
    print('arr:', id(arr))     # --> arr: 2194854342160
    print('brr:', id(brr))     # --> brr: 2194854342160
    # 不复制数组到新的内存,即brr也是引用arr所引用的内存地址
    
    brr[1] = 25
    
    print('arr:', arr)      # --> arr:[ 1 25  3  4]
    print('brr:', brr)      # --> brr:[ 1 25  3  4]
    
    • 注意:
      • 开启复制参数,会产生副本,需要开辟新的内存空间进行存储。如果数据量比较大,会造成资源浪费
  • 创建数组,设置ndim参数
    arr5 = np.array([1,2,3], ndmin=2)
    print(arr5)
    
    # ---> 输出结果
    [[1 2 3]]
    
  • 创建数组,设置subok参数
    # 创建矩阵
    a_mat = np.mat([1, 2, 3])
    
    # 复制一个矩阵
    arr_f = np.array(a_mat, subok=False)    # False,创建的副本类型为数组ndarray
    arr_t = np.array(a_mat, subok=True)     # True, 创建的副本类型为矩阵matrix
    
    print('a_mat', type(a_mat))             # --> a_mat <class 'numpy.matrix'>
    print('arr_f', type(arr_f))             # --> arr_f <class 'numpy.ndarray'>
    print('arr_t', type(arr_t))             # --> arr_t <class 'numpy.matrix'>
    
创建区间数组
  • 语法
    numpy.arange(start, stop, step, dtype)
    
    # 参数说明
        # start     # 起始值,默认是0
        # stop      # 终止值,不包含
        # step      # 步长,默认是1
        # dtype     # 设置返回ndarray的数据类型,如果不设置,则使用输入数据的类型
    
  • 示例
    # python原生代码range
    range(3.1)
    # 报错:TypeError: 'float' object cannot be interpreted as an integer
    
    # numpy创建区间数组
    a = np.arange(3.9)
    print(a)    # --> [0. 1. 2. 3.]
    
    a = np.arange(3)
    print(a)    # --> [0 1 2]
    
    a = np.arange(0, 10, 2)
    print(a)    # --> [0 2 4 6 8]
    a = np.arange(10, step=2)
    print(a)    # --> [0 2 4 6 8]
    
    a = np.arange(10, step=2, dtype=float)
    b = np.arange(10, step=2, dtype=int)
    print(a)    # --> [0. 2. 4. 6. 8.]
    print(b)    # --> [0 2 4 6 8]
    
    # 创建一个从0.1开始的,步长为0.1,长度为3的数组
    a = np.arange(0.1, 0.4, 0.1)
    print(a)    # --> [0.1 0.2 0.3 0.4]
    
    # 从结果可以看到,并不是我们想要的
    # 原因:在python中,浮点数的计算是先转换成二进制进行计算,再转换回来
    print(0.1 + 0.2)    # --> 0.30000000000000004
    
    # 解决方法:先用整数进行运算,然后再换算成浮点数
    a = np.arange(1, 4, 1) / 10
    print(a)
    
创建等差数列数组
  • 语法
    # 返回在间隔start和stop上计算的num个均匀间隔的数组(数组是一个等差数量构成)
    
    numpy.linspace(start, stop, num=50, endpoint=True, retstep=False, dtype=None,
         axis=0)
    
    # 参数说明
        # start         # 必填,序列的起始值
        # stop          # 必填,序列的终止值
        # num           # 要生成的等步长的样本数量,默认50
        # endpoint      # 数量是否包含stop值,默认是True
        # retstep       # 生成的数组中是否显示步长
        # dtype         # 设置生成的ndarray的数据类型
        # axis          # 
    
  • 示例1
    # 起始值为1,终止值为10,数量个数为5
    a = np.linspace(1, 10, 5)
    print(a)    # --> [ 1.    3.25  5.5   7.75 10.  ]
    
    # 使用等差数量输出 0 0.5 1 1.5 2 2.5 3 3.5 4
    a = np.linspace(0, 4, 9)
    print(a)    # --> [0.  0.5 1.  1.5 2.  2.5 3.  3.5 4. ]
    
  • 示例2
    # 设置retstep参数,显示步长
    a = np.linspace(0, 4, 9, retstep=True)
    print(a)
    
    # 输出结果
    (array([0. , 0.5, 1. , 1.5, 2. , 2.5, 3. , 3.5, 4. ]), 0.5)
    
  • 用法:常用于线性回归的样本集
    # 生成x_data,值为(0,100]之间500个等差数列书记集合作为样本特征
    # 根据目标线性方程y=3\*x+2,生成相应的标签集合y_dat
    
    x_data = np.linspace(0, 100, 500, endpoint=False)
    print(x_data)
    
    y_data = 3 * x_data + 2
    print(y_data)
    
创建等比数列数组
  • 语法
    # 返回在间隔start和stop上计算的num个均匀间隔的数组(数组是一个等比数列构成)
    
    numpy.logspace(start, stop, num=50, endpoint=True, base=10.0, dtype=None, axis=0)
    
    # 参数说明
        # start         # 必填,序列的起始值
        # stop          # 必填,序列的终止值
        # num           # 要生成的等步长的样本数量,默认50
        # endpoint      # 数量是否包含stop值,默认是True
        # base          # 对数log的底数
        # dtype         # 设置生成的ndarray的数据类型
        # axis          # 
    
  • 示例
    a = np.logspace(0, 9, 10, base=2)
    print(a)
    
    # 输出结果
    [  1.   2.   4.   8.  16.  32.  64. 128. 256. 512.]
    
    # base=2 指定底数是2
    # [2^0, 2^1, 2^2, 2^3, 2^4, 2^5, 2^6, 2^7, 2^8, 2^9]
    
创建全0数列数组
  • 语法
    # 创建指定大小的数组,数组元素以0来填充,默认元素是浮点型
    numpy.zeros(shape, dtype=None, order='C', *args, **kwargs)
    
    # 参数说明
        # shape          # 数组形状
        # dtype          # 设置生成的ndarray的数据类型
        
    
    # 返回具有与给定数组相同的形状和类型的全0数组
    numpy.zeros_like(arr)
    
  • 示例1
    # 指定数组形状是一维数组:1行5列
    a = np.zeros(5)     # --> np.zeros((5,)) 
    print(a)
    
    # 输出结果
    [0. 0. 0. 0. 0.]
    
    
    # 指定数组形状是二维数组:2行3列
    a = np.zeros((2, 3))
    print(a)
    
    # 输出结果
    [[0. 0. 0.]
     [0. 0. 0.]]
     
     
    # 指定数组形状是三维数组:2块2行3列
    a = np.zeros((2, 2, 3))
    print(a)
    
    # 输出结果
    [[[0. 0. 0.]
      [0. 0. 0.]]
    
     [[0. 0. 0.]
      [0. 0. 0.]]]
    
  • 示例2
    a = np.zeros(5, dtype=int)
    print(a)
    
    # 输出结果
    [0 0 0 0 0]
    
  • 示例3
    arr = np.array([[1,2,3],[4,5,6]])
    # arr是一个2行3列的二维数组
    
    a = np.zeros_like(arr)
    print(a)
    
    # 输出结果
    [[0 0 0]
     [0 0 0]]
    
创建全1数列数组
  • 语法
    # 创建指定大小的数组,数组元素以1来填充,默认元素是浮点型
    numpy.ones(shape, dtype=None, order='C', *args, **kwargs)
    
    # 参数说明
        # shape          # 数组形状
        # dtype          # 设置生成的ndarray的数据类型
        
    
    # 返回具有与给定数组相同的形状和类型的全1数组
    numpy.ones_like(arr)
    
  • 示例
    a = np.ones(5)
    print(a)
    
    # 输出结果
    [1. 1. 1. 1. 1.]
    
    
    a = np.ones(5, dtype=int)
    print(a)
    
    # 输出结果
    [1 1 1 1 1]
    
    
    arr = np.array([[1,2,3],[4,5,6]])
    # arr是一个2行3列的二维数组
    
    a = np.ones_like(arr)
    print(a)
    
    # 输出结果
    [[1 1 1]
     [1 1 1]]
    

数组属性
  • 数组属性
    ndarray.ndim            # 秩,即轴的数量或维度的数量
    ndarray.shape           # 数组的维度,对于矩阵,n行m列
    ndarray.size            # 数组元素的总个数,相当于.shape中n * m 的值
    ndarray.itemsize        # ndarray对象中每个元素的大小,以字节为单位
    ndarray.dtype           # ndarray对象的元素类型
    ndarray.astype(type)    # 强制转换数据类型
    ndarray.flags           # ndarray对象的内存信息
        # flags属性值
        # C_CONTIGUOUS (C)  # 数据是在一个单一的C风格的连续段中
        # F_CONTIGUOUS (F)  # 数据是在一个单一的Fortran风格的连续段中
        # OWNDATA (O)       # 数组拥有它所使用的内存或从另一个对象中借用它
        # WRITEABLE (W)     # 数据区域可以被写入,将该值设置为 False,则数据为只读
        # ALIGNED (A)       # 数据和所有元素都适当地对齐到硬件上
        # UPDATEIFCOPY (U)  # 这个数组是其它数组的一个副本,当这个数组被释放时,原数组的内容将被更新
    ndarray.real            # ndarray元素的实部
    ndarray.imag            # ndarray元素的虚部
    ndarray.data            # 包含实际数组元素的缓冲区
        # 由于一般通过数组的索引获取元素,所以通常不需要使用这个属性。
    
  • 示例
    # 一维数组,1行12列
    a = np.array([11, 12, 13, 14, 15, 16, 21, 22, 23, 24, 25, 26])
    
    print(a.ndim)           # --> 1             # 1维
    print(a.shape)          # --> (12,)         # 1行12列
    print(a.size)           # --> 12            # 12个元素
    print(a.itemsize)       # --> 4             # int32类型4个字节
    print(a.dtype)          # --> int32         # ndarray元素类型
    
    
    # 二维数组,2行6列
    a = np.array([[11, 12, 13, 14, 15, 16], [21, 22, 23, 24, 25, 26]])
    
    print(a.ndim)           # --> 2         # 2维
    print(a.shape)          # --> (2, 6)    # 2行6列
    print(a.size)           # --> 12        # 12个元素
    print(a.itemsize)       # --> 4         # int32类型4个字节
    print(a.dtype)          # --> int32     # ndarray元素类型
    
    
    # 三维数组,2块2行3列
    a = np.array([
                [[11, 12, 13],
                 [14, 15, 16]],
    
                [[21, 22, 23],
                 [24, 25, 26]]
                ])
    
    print(a.ndim)           # --> 3             # 3维
    print(a.shape)          # --> (2,2,3)       # 2块2行3列
    print(a.size)           # --> 12            # 12个元素
    print(a.itemsize)       # --> 4             # int32类型4个字节
    print(a.dtype)          # --> int32         # ndarray元素类型
    

调整维度
  • 调整维度
    # 不改变原数组,生成新的副本
    ndarray.reshape(shape, order='C')           # 元素个数不够时,会报错
    numpy.resize(a, new_shape)                  # 元素个数不够时,会循环原数组元素进行取值
    
    # 直接修改原数组
    ndarray.reshape = (shape)                   # 元素个数不够时,会报错
    ndarray.resize(new_shape, refcheck=True)    # 元素个数不够时,会用0进行补充
        # new_shape     # 调整数组大小的形状
        # refcheck      # 如果为False,则不检查引用计数。默认为True
    
  • 示例
    # 元素个数足够
    a = np.arange(20)
    print('a:', a)
    
    b = a.reshape((2,10))
    print('b:', b)
    
    c = np.resize(a, (2, 10))
    print('c:',c)
    
    a.shape = (2,10)
    print('a:', a)
    
    a.resize((2, 10), refcheck=True)
    print('a:', a)
    
    # 输出结果
    a: [ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19]
    
    b: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]]
    
    c: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]]
    
    a: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]]
         
    a: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]]
     
     
    # 元素个数不够
    a = np.arange(20)
    print('a:', a)
    
    # 元素个数超出原数组,会报错
    # b = a.reshape((3,10))
    # print('b:', b)
    
    c = np.resize(a, (3, 10))
    print('c:',c)
    
    # 元素个数超出原数组,会报错
    # a.shape = (3, 10)
    
    a.resize((3, 10), refcheck=True)
    print('a:', a)
    
    # 输出结果
    a: [ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19]
    
    b:报错,ValueError: cannot reshape array of size 20 into shape (3,10)
    
    c: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]
         [ 0  1  2  3  4  5  6  7  8  9]]
    
    # 报错,ValueError: cannot reshape array of size 20 into shape (3,10)
    
    a: [[ 0  1  2  3  4  5  6  7  8  9]
         [10 11 12 13 14 15 16 17 18 19]
         [ 0  0  0  0  0  0  0  0  0  0]]
    

数据类型
  • NumPy提供了比Python更加丰富的数据类型,基本上可以和C语言的数据类型对应上,其中部分类型对应为Python内置的类型
  • 常用NumPy基本类型
    数据类型语言描述
    bool_布尔型数据类型(True 或者 False)
    int_默认整数类型,类似于 C 语言中的 long,取值为 int32 或 int64
    intc和 C 语言的 int 类型一样,一般是 int32 或 int 64
    intp用于索引的整数类型(类似于 C 的 ssize_t,通常为int32 或 int64)
    int8代表与1字节相同的8位整数
    值的范围是-128到127
    int16代表 2 字节(16位)的整数
    范围是-32768至32767
    int32代表 4 字节(32位)整数
    范围是-2147483648至2147483647
    int64表示 8 字节(64位)整数
    范围是-9223372036854775808至9223372036854775807
    uint8代表1字节(8位)无符号整数(正整数)
    uint162 字节(16位)无符号整数(正整数)
    uint324 字节(32位)无符号整数(正整数)
    uint648 字节(64位)无符号整数(正整数)
    float_float64 类型的简写。
    float16半精度浮点数,包括:1 个符号位,5 个指数位,10个尾数位
    float32单精度浮点数,包括:1 个符号位,8 个指数位,23个尾数位
    float64双精度浮点数,包括:1 个符号位,11 个指数位,52个尾数位
    complex_复数类型,与 complex128 类型相同
    complex64表示实部和虚部共享 32 位的复数
    complex128表示实部和虚部共享 64 位的复数
    str_表示字符串类型
    string_表示字节串类型
    object表示可变类型(类型和长度均为可变)
  • NumPy的数值类型实际上是dtype对象的实例,并对应唯一的字符,包括np.bool_np.int32np.float32等等
  • 数据类型对象 (dtype)
    • 数据类型对象(Data Type Object)又称dtype对象,主要用来描述数组元素的数据类型、大小以及字节顺序
    • 数据类型对象(NumPy.dtype 类的实例)用来描述与数组对应的内存区域是如何使用,它描述了数据的以下几个方面
      • 数据的类型(整数,浮点数或者Python对象)
      • 数据的大小(例如, 整数使用多少个字节存储)
      • 数据的字节顺序(小端法或大端法)
      • 在结构化类型的情况下,字段的名称、每个字段的数据类型和每个字段所取的内存块的部分
      • 如果数据类型是子数组,那么它的形状和数据类型是什么
    • 字节顺序是通过对数据类型预先设定<>来决定的。
      • <:意味着小端法(最小值存储在最小的地址,即低位组放在最前面)。
      • >:意味着大端法(最重要的字节存储在最小的地址,即高位组放在最前面)。
    • dtype 对象是使用以下语法构造的:
      numpy.dtype(object, align, copy)
      
      # 参数说明
          # object    # 要转换为的数据类型对象
          # align     # 如果为 true,填充字段使其类似C的结构体。
          # copy      # 复制dtype对象,如果为false,则是对内置数据类型对象的引用
      
    • 关于字节长度
      • 每个字节长度为8 bits
      • 如:一个元素类型为float64,这个元素占用64 bits,字节长度为 64/8 = 8字节
      • int8、int16、int32、int64 四种数据类型可以使用字符串 ‘i1’, ‘i2’,‘i4’,‘i8’ 代替
  • 数据类型标识码
    • NumPy中每种数据类型都有一个唯一标识的字符码
      标识码对应类型
      b代表布尔型
      i带符号整型
      u无符号整型
      f浮点型
      c复数浮点型
      m时间间隔(timedelta)
      Mdatatime(日期时间)
      Oobject对象(可变类型)
      Sbyte-字节串(S)
      abyte-字符串(a)
      UUnicode
      V原始数据(void)
  • 定义结构化数据
  • 通常情况下,结构化数据使用字段的形式来描述某个对象的特征
  • 个人理解:创建二维表的表头,并指定数据列的类型以及长度
  • 示例:记录人员信息(姓名、性别、年龄、工资)
    name:str
    gender:str
    age:int
    salary:float
    
  • 定义结构化数据
    import numpy as np
    
    dt = np.dtype([('name', 'S20'),('gender','S1'),('age','i1'),('salary','f4')])
    
    print('dt:', dt)
    
    a = np.array([('张三', '男', 28, 3890.65), ('李四', '男', 38, 2850.00), ('赵丽', '女', 22, 4300.00)], dtype=dt)
    
    print('a:', a)
    print("a['name'][0]:", a['name'][0])
    print("a['name'][1]:", a['name'][1])
    print("a['name'][2]:", a['name'][2])
    
    print("a['gender'][0]:", a['gender'][0])
    print("a['gender'][1]:", a['gender'][1])
    print("a['gender'][2]:", a['gender'][2])
    
    print("a['age'][0]:", a['age'][0])
    print("a['age'][1]:", a['age'][1])
    print("a['age'][2]:", a['age'][2])
    
    print("a['salary'][0]:", a['salary'][0])
    print("a['salary'][1]:", a['salary'][1])
    print("a['salary'][2]:", a['salary'][2])
    
    
    # 输出结果
    dt:[('name', '<U20'), ('gender', '<U1'), ('age', 'i1'), ('salary', '<f4')]
    a: [('张三', '男', 28, 3890.65) ('李四', '男', 38, 2850.  ) ('赵丽', '女', 22, 4300.  )]
    a['name'][0]: 张三
    a['name'][1]: 李四
    a['name'][2]: 赵丽
    
    a['gender'][0]: 男
    a['gender'][1]: 男
    a['gender'][2]: 女
    
    a['age'][0]: 28
    a['age'][1]: 38
    a['age'][2]: 22
    
    a['salary'][0]: 3890.65
    a['salary'][1]: 2850.0
    a['salary'][2]: 4300.0
    
    
  • int和uint的区别
    import numpy as np
    
    dt1 = np.dtype([('num', 'i1')])
    dt2 = np.dtype([('num', 'u1')])
    
    arr_a = np.array([11], dtype=dt1)       # ---> [(11,)]
    arr_b = np.array([11], dtype=dt2)       # ---> [(11,)]
    print(arr_a)
    print(arr_b)
    
    
    arr_c = np.array([-11], dtype=dt1)      # ---> [(-11,)]
    # arr_d = np.array([-11], dtype=dt2)      # ---> 报错
    print(arr_c)
    # print(arr_d)
    
    
    # int类型可以存正整数和负整数
    # uint类型只能存正整数
    
  • 可变数据类型和长度
    • 当数组的数据类型指定为特定的某种类型时,数组就只能存储指定类型的数据(或者在可以转换的前提下,会将你存储的数据转换成指定数据类型,比如将数字转换成字符串)
    • 当数组的数据类型指定为可变类型(object)时,数组内可以存放任意类型、任意长度的数据
    • 示例1
    import numpy as np
    
    dt1 = np.dtype([('name', 'U2')])
    dt2 = np.dtype([('name', object)])
    
    arr_a = np.array(['张三', '李四', '王小花', '李傲梅', '欧阳吹风'], dtype=dt1)
    arr_b = np.array(['张三', '李四', '王小花', '李傲梅', '欧阳吹风'], dtype=dt2)
    
    arr_c = np.array([1, 2, 3, 4, 5566, 98921831, 'ss'], dtype=dt1)
    arr_d = np.array([1, 2, 3, 4, 5566, 98921831, 'ss'], dtype=dt2)
    
    print(arr_a)                            # ---> [('张三',) ('李四',) ('王小',) ('李傲',) ('欧阳',)]
    print(arr_b)                            # ---> [('张三',) ('李四',) ('王小花',) ('李傲梅',) ('欧阳吹风',)]
    print(arr_c)                            # ---> [('1',) ('2',) ('3',) ('4',) ('55',) ('98',) ('ss',)]
    print(arr_d)                            # ---> [(1,) (2,) (3,) (4,) (5566,) (98921831,)]
    
    print(type(arr_a['name'][0]))           # ---> <class 'numpy.str_'>
    print(type(arr_b['name'][0]))           # ---> <class 'str'>
    
    print(type(arr_c['name'][0]))           # ---> <class 'numpy.str_'>
    print(type(arr_d['name'][0]))           # ---> <class 'int'>
    
    print(type(arr_c['name'][6]))           # ---> <class 'numpy.str_'>
    print(type(arr_d['name'][6]))           # ---> <class 'str'>
    
    • 示例2
    import numpy as np
    
    arr_a = np.array([['张三', '男', 23, 5300], ['赵丽', '女', 22, 5500], ['王帅', '男', 28, 6000]])
    # print(arr_a, arr_a.dtype)
    # [['张三' '男' '23' '5300']
    #  ['赵丽' '女' '22' '5500']
    #  ['王帅' '男' '28' '6000']]
    # <U11
    # 不指定数组类型时,默认将所有数据转换成数组内元素所有类型占用内存最大的
    
    arr_b = np.array([['张三', '男', 23, 5300], ['赵丽', '女', 22, 5500], ['王帅', '男', 28, 6000]], dtype='U8')
    # print(arr_b, arr_b.dtype)
    # [['张三' '男' '23' '5300']
    #  ['赵丽' '女' '22' '5500']
    #  ['王帅' '男' '28' '6000']]
    # <U8
    # 指定类型后,数组所有元素均以指定类型存储(可以类型互转的情况下,类型不同的会自动转换成指定类型)
    
    # arr_c = np.array([['张三', '男', 23, 5300], ['赵丽', '女', 22, 5500], ['王帅', '男', 28, 6000]], dtype='u8')
    # print(arr_c, arr_c.dtype)
    # 报错:invalid literal for int() with base 10: '张三'
    # 原因:字符串类型不能转换成int类型
    
    arr_d = np.array([['张三', '男', 23, 5300], ['赵丽', '女', 22, 5500], ['王帅', '男', 28, 6000]], dtype=object)
    # arr_d = np.array([['张三', '男', 23, 5300], ['赵丽', '女', 22, 5500], ['王帅', '男', 28, 6000]], dtype='O')
    print(arr_d, arr_d.dtype)
    # [['张三' '男' 23 5300]
    #  ['赵丽' '女' 22 5500]
    #  ['王帅' '男' 28 6000]]
    # object
    
    # 当数据类型指定为object时,数组内的数据不会强制转换类型,会按照原本的类型进行存储
    
    注意:
    指定类型不灵活,但是效率高
    可变类型灵活,但是效率低

ndarray对象的秩、轴、维度

  • 在NumPy中,一个数组的“秩”是其维度的数量,而轴是每个维度的表示。维度,又称作长度,是指数组在某一轴上的长度。
  • 秩(秩)
    • NumPy数组的秩可以通过数组的ndim属性获得。
    import numpy as np
     
    arr = np.array([[1, 2, 3], [4, 5, 6]])
    print("数组的秩(秩):", arr.ndim)
    
    # 输出: 数组的秩(秩): 2
    
  • 轴(axes)
    • 对于n维数组,轴是从0开始的整数,表示数组在哪个维度上进行操作。
    import numpy as np
     
    arr = np.array([[1, 2, 3], [4, 5, 6]])
    print("轴:", list(range(arr.ndim)))
    
    # 输出: 轴: [0, 1]
    
  • 维度(长度)
    • 维度是指数组在某一轴上的长度。可以通过数组的shape属性获得。
    import numpy as np
     
    arr = np.array([[1, 2, 3], [4, 5, 6]])
    print("维度:", arr.shape)
    
    # 输出: 维度: (2, 3)
    
  • 注意:在NumPy中,维度是通过数组的shape属性获得的,它返回一个元组,元组中的每一个元素都代表了数组在一个特定轴(维度)上的长度

数组操作
切片和索引
  • ndarray对象的内容可以通过索引或切片来访问和修改,与Python中List的切片操作一样
  • ndarray数组可以基于0 ~ n 的下标进行索引array[n]
  • 注意:
    • 与列表的区别在于,数组切片是基于原始数组视图(就是做任何修改,原始数组都会跟着改变)
    • 如果不想改变原始数组,那就需要进行显示复制,从而对副本进行操作(.copy()
  • 示例:数组切片是基于原始数组视图
    import numpy as np
    
    ls_arr = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
    np_arr = np.arange(10)
    
    print('=====切片前=====')
    print('ls_arr:', ls_arr)
    print('np_arr:', np_arr)
    
    ls_brr = ls_arr[1:5]
    np_brr = np_arr[1:5]
    
    print('=====切片结果=====')
    print('ls_brr:', ls_brr)
    print('np_brr:', np_brr)
    
    print('=====修改brr后=====')
    ls_brr[1] = 888
    np_brr[1] = 888
    
    print('ls_brr:', ls_brr)
    print('np_brr:', np_brr)
    print('')
    print('ls_arr:', ls_arr)
    print('np_arr:', np_arr)
    
    # 输出结果
    =====切片前=====
    ls_arr: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
    np_arr: [0 1 2 3 4 5 6 7 8 9]
    
    =====切片结果=====
    ls_brr: [1, 2, 3, 4]
    np_brr: [1 2 3 4]
    
    =====修改brr后=====
    ls_brr: [1, 888, 3, 4]
    np_brr: [  1 888   3   4]
    
    ls_arr: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
    np_arr: [  0   1 888   3   4   5   6   7   8   9]
    
  • 解决方法:使用copy()
    import numpy as np
    # np_crr = np_arr[1:5].copy()
    np_crr = np_arr.copy()[1:5]
    print('np_crr:', np_crr)
    
    np_crr[1] = 9999
    print('np_crr:', np_crr)
    print('np_arr:', np_arr)
    
    # 输出结果
    np_crr: [1 2 3 4]
    
    np_crr: [   1 9999    3    4]
    np_arr: [0 1 2 3 4 5 6 7 8 9]
    
  • 为什么切片和区间操作含头不含尾
    • 当只有最后一个位置信息时,我们可以快速看出切片和区间里有几个元素

      np_arr[:3]          # 可以快速看出切片后的数组元素是3个
      np.arange(3)        # 可以快速看出通过区间生成的数组元素是3个
      
    • 当起始位置信息都可见时,我们可以快速计算出切片和区间的长度,stop - start

      np_arr[1:5]         # 可以快速计算出切片后数组元素个数, 5 - 1 = 4
      np_arr[-1, -8]
      
    • 这样做也让我们可以利用任意一个下标把序列分割成不重叠的两部分,只要写成my_list[:x)和my_listlx:]就可以了

切片语法
  • 一维数组
    • 一维数组的切片语法与列表的切片语法一致
    arr[start():stop(不含):step]
    
    
    # 从前往后,索引从0开始,1, 2, ......
    # 从后往前,索引从-1开始,-2, -3, ......
    arr = arange(10)    # [0 1 2 3 4 5 6 7 8 9]
    arr[:-2]            # 表示从第1个元素开始(索引为0),到倒数第二个元素(不含)  [0 1 2 3 4 5 6 7]
    
    # 步长为负数,表示从后往前切
    arr = arange(10)    # [0 1 2 3 4 5 6 7 8 9]
    
    arr[10:1:-1]        # 表示从倒数第一个元素开始,从后往前,到第二个元素(不含)  [9 8 7 6 5 4 3 2]
    np_arr[-1:-8:-1]    # 表示从倒数第一个元素开始,从后往前,到倒数第八个元素(不含) [9 8 7 6 5 4 3]
    
  • 多维数组
    # 使用索引号取值
        arr[row_index][column_index]
    
    # 使用索引号切片
        np_arr[row_start:row_stop:step, col_start:col_stop:step]
    
    # 使用省略号:...
        np_arr[..., col_start:col_stop:step]        # 在行索引位置使用...表示切所有行元素
        np_arr[row_start:row_stop:step, ...]        # 在列索引位置使用...表示切所有列元素
        
    # 使用整数数组索引
        np_arr[ar1, ar2]
        # 分别取出np_arr[ar1[0],ar2[0]]、np_arr[ar1[1],ar2[1]]、...np_arr[ar1[n],ar2[n]]的元素组成一个新数组
    
数组切片示例
一维数组
  • 示例
    import numpy as np
    
    # 创建原始数组
    np_arr = np.arange(10)
    print('np_arr', np_arr)       # --> np_arr [0 1 2 3 4 5 6 7 8 9]
    
    np_brr = np_arr[:5]
    print('np_brr',np_brr)       # --> np_brr [0 1 2 3 4]
    
    np_brr = np_arr[1:5]
    print('np_brr',np_brr)       # --> np_brr [1 2 3 4]
    
    np_brr = np_arr[::2]
    print('np_brr',np_brr)       # --> np_brr [0 2 4 6 8]
    
  • 索引-1和步长-1
    import numpy as np
    np_arr = np.arange(10)
    print('np_arr', np_arr)
    
    np_brr = np_arr[:-1]
    print('np_brr', np_brr)
    
    np_crr = np_arr[::-1]
    print('np_crr', np_crr)
    
    # 输出结果
    np_arr [0 1 2 3 4 5 6 7 8 9]
    np_brr [0 1 2 3 4 5 6 7 8]
    np_crr [9 8 7 6 5 4 3 2 1 0]
    
多维数组
  • 使用索引取值方式

  • 语法

    np_arr[row_index][column_incex]
    
  • 示例

    import numpy as np
    
    # 创建一个4行5列的二维数组
    np_arr = np.arange(20).reshape(4, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    # np_arr[row_index][column_index]
    np_brr = np_arr[2][3]
    # 拆分理解
    # 第一步:np_brr = np_arr[row_index]    # 根据索引取得下一维度的一个元素,获取一个一维数组
    np_temp = np_arr[2]
    print(np_temp)       # -->  [10 11 12 13 14]
    
    # 第二步:np_temp[column_index]          # 根据第二个索引,从获取到的一维数组中取得一个元素
    np_brr = np_temp[3]
    print(np_brr)       # --> 13
    
    np_crr = np_arr[2][3]
    print(np_crr)       # --> 13
    
  • 使用索引切片方式

  • 语法

    np_arr[row_start:row_stop:step, col_start:col_stop:step]
    
  • 示例

    import numpy as np
    
    # 创建一个4行5列的二维数组
    np_arr = np.arange(20).reshape(4, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    # np_arr[row_start:row_stop:step, col_start:col_stop:step]
    
    np_temp = np_arr[1:, 2:]         # --> 切索引号是1之后的所有行, 切索引号为2之后的所有列
    print(np_temp)
    # 返回结果
    # [[ 7  8  9]
    #  [12 13 14]
    #  [17 18 19]]
    
    # 拆分理解
    # 第一步:切取索引号是1之后的所有行
    # [[ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    # 第二步:切索引号为2之后的所有列
    # [[ 7  8  9]
    #  [12 13 14]
    #  [17 18 19]]
    
  • 使用省略号获取所有元素

  • 语法

    np_arr[..., col_start:col_stop:step]
    np_arr[row_start:row_stop:step, ...]
    
  • 示例1

    # 创建一个4行5列的二维数组
    np_arr = np.arange(20).reshape(4, 5)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np_temp = np_arr[..., 1]        # 切所有行元素,切索引号为1的列的所有元素
    print(np_temp)
    # [ 1  6 11 16]
    
  • 拆分理解

    • 第一步:获取到所有行元素

      • 在这里插入图片描述
    • 第二步:获取索引号为1的列的所有元素

      • 在这里插入图片描述
    • 最终结果

      • 在这里插入图片描述
  • 示例2

    import numpy as np
    
    np_arr = np.arange(20).reshape(4, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    print('')
    np_brr1 = np_arr[..., 1:]
    print(np_brr1)
    # [[ 1  2  3  4]
    #  [ 6  7  8  9]
    #  [11 12 13 14]
    #  [16 17 18 19]]
    
    print('')
    np_brr2 = np_arr[..., 1::2]
    print(np_brr2)
    # [[ 1  3]
    #  [ 6  8]
    #  [11 13]
    #  [16 18]]
    
  • np_arr[n, m]np_arr[n][m]的区别

  • 示例

    import numpy as np
    
    
    np_arr = np.arange(20).reshape(4, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    print('np_arr[m, n]:', np_arr[2, 3])          # ---> 13
    print('np_arr[m][n]:', np_arr[2][3])          # ---> 13
    
    # 两次的结果是完全一样的,实际原理是不一样的
    # np_arr[2, 3], 是取数组中行索引为2, 列索引为3的元素
    # np_arr[2][3], 是先从数组中取出索引为2元素,再从取出的元素中取索引为3的元素
    
    print('')
    print('np_arr[m, n]:', np_arr[..., 3])          # ---> [ 3  8 13 18]
    print('np_arr[m][n]:', np_arr[...][3])          # ---> [15 16 17 18 19]
    
    # 这里就可以明显看出来结果不一样了
    # np_arr[..., 3] 是取数组中所有行索引,列索引为3的元素
    # np_arr[...][3] 是先取所有元素组成一个新数组,再从新数组中取索引为3的元素
    
  • 整数数组索引

  • 语法

    np_arr[ar1, ar2]
    
  • 示例1

    import numpy as np
    
    np_arr = np.arange(20).reshape(4, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np_brr = np_arr[[0, 1, 3], [0, 2, 4]]
    
    print(np_brr)       # ---> [ 0  7 19]
    
    # 分别获取np_arr中 (0, 0)、(1,2)、(3,4)的元素
    
    • 在这里插入图片描述
  • 示例2:获取5*6数组中四个顶角位置的元素

    import numpy as np
    
    np_arr = np.arange(30).reshape(5, 6)
    print(np_arr)
    # [[ 0  1  2  3  4  5]
    #  [ 6  7  8  9 10 11]
    #  [12 13 14 15 16 17]
    #  [18 19 20 21 22 23]
    #  [24 25 26 27 28 29]]
    
    # 四个顶角位置的元素为:0,5,24,29
    # 这四个顶角的位置坐标为:(0,0) (0,5) (4,0) (4,5)
    
    np_brr = np_arr[[0, 0, 4, 4], [0, 5, 0, 5]]
    print(np_brr)  # ---> [ 0  5 24 29]
    
    print(np_brr.reshape(2,2))
    # [[ 0  5]
    #  [24 29]]
    
  • 示例3:创建一个国际象棋棋盘(8 * 8),白色用0表示,黑色用1表示

    • 在这里插入图片描述
    import numpy as np
    
    # 先生成一个8*8的全0数组,或者全1数组
    np_arr = np.zeros(8 * 8).reshape(8, 8)
    # print(np_arr)
    # [[0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]]
    
    # 根据棋盘样式,修改数组内元素为1
    
    # 使用原生python循环
    # for row in range(np_arr.shape[0]):
    #     for col in range(np_arr.shape[1]):
    #         if row % 2:
    #             # 奇数行
    #             if not col % 2:
    #                 # 偶数列
    #                 np_arr[row, col] = 1
    #         else:
    #             # 偶数行
    #             if col % 2:
    #                 np_arr[row, col] = 1
    # print(np_arr)
    # # [[0. 1. 0. 1. 0. 1. 0. 1.]
    # #  [1. 0. 1. 0. 1. 0. 1. 0.]
    # #  [0. 1. 0. 1. 0. 1. 0. 1.]
    # #  [1. 0. 1. 0. 1. 0. 1. 0.]
    # #  [0. 1. 0. 1. 0. 1. 0. 1.]
    # #  [1. 0. 1. 0. 1. 0. 1. 0.]
    # #  [0. 1. 0. 1. 0. 1. 0. 1.]
    # #  [1. 0. 1. 0. 1. 0. 1. 0.]]
    
    # 使用numpy
    np_arr[1::2, ::2] = 1
    print(np_arr)
    # [[0. 0. 0. 0. 0. 0. 0. 0.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 0. 0. 0. 0. 0. 0. 0.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]]
    
    np_arr[::2, 1::2] = 1
    print(np_arr)
    # [[0. 1. 0. 1. 0. 1. 0. 1.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 1. 0. 1. 0. 1. 0. 1.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 1. 0. 1. 0. 1. 0. 1.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]
    #  [0. 1. 0. 1. 0. 1. 0. 1.]
    #  [1. 0. 1. 0. 1. 0. 1. 0.]]
    
    • 这个案例明显就可以看到numpy的强大,实现同样的效果
      • 原生python代码使用循环+判断
      • numpy使用两句就解决了
  • 布尔数组索引

  • 语法

    np_arr[Expression]
    np_arr[(Expression1) & (Expression2)]
    np_arr[(Expression1) | (Expression2)]
    
  • 示例1:获取数组中大于20的元素

    # 获取数组np_arr中大于20的元素
    
    import numpy as np
    
    np_arr = np.array([0, 22, 3, 15, 63, 76, 2, 16, 31])
    print(np_arr)   # ---> [ 0 22  3 15 63 76  2 16 31]
    
    np_brr = np_arr[np_arr > 20]
    print(np_brr)   # ---> [22 63 76 31]
    
    # -------------------------------------
    np_arr = np_arr.reshape(3, 3)
    print(np_arr)
    # [[ 0 22  3]
    #  [15 63 76]
    #  [ 2 16 31]]
    
    # 获取数组np_arr中大于20的元素
    np_brr = np_arr[np_arr > 20]
    print(np_brr)   # ---> [22 63 76 31]
    
  • 示例2:获取数组中的奇数

    import numpy as np
    
    np_arr = np.arange(50).reshape(10, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]
    #  [20 21 22 23 24]
    #  [25 26 27 28 29]
    #  [30 31 32 33 34]
    #  [35 36 37 38 39]
    #  [40 41 42 43 44]
    #  [45 46 47 48 49]]
    
    np_brr = np_arr[np_arr % 2 == 1]
    print(np_brr)
    # [ 1  3  5  7  9 11 13 15 17 19 21 23 25 27 29 31 33 35 37 39 41 43 45 47 49]
    
  • 示例3:获取数组中大于10,且小于30的元素

    import numpy as np
    
    np_arr = np.arange(50).reshape(10, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]
    #  [20 21 22 23 24]
    #  [25 26 27 28 29]
    #  [30 31 32 33 34]
    #  [35 36 37 38 39]
    #  [40 41 42 43 44]
    #  [45 46 47 48 49]]
    
    np_brr = np_arr[(np_arr > 10) & (np_arr < 30)]
    # np_brr = np_arr[(np_arr > 10) & (np_arr <= 30)]
    print(np_brr)
    # [11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29]
    
  • 示例4:获取数组中小于10,或者大于30的元素

    import numpy as np
    
    np_arr = np.arange(50).reshape(10, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]
    #  [20 21 22 23 24]
    #  [25 26 27 28 29]
    #  [30 31 32 33 34]
    #  [35 36 37 38 39]
    #  [40 41 42 43 44]
    #  [45 46 47 48 49]]
    
    # 使用 |(或)
    np_brr = np_arr[(np_arr < 10) | (np_arr > 30)]
    
    # 使用 ~(取反)
    np_brr = np_arr[~((np_arr > 10) & (np_arr < 30))]
    print(np_brr)
    # [ 0  1  2  3  4  5  6  7  8  9 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49]
    
  • 示例5:直接使用TrueFalse

    import numpy as np
    
    np_arr = np.arange(24).reshape(4, 6)
    print(np_arr)
    # [[ 0  1  2  3  4  5]
    #  [ 6  7  8  9 10 11]
    #  [12 13 14 15 16 17]
    #  [18 19 20 21 22 23]]
    
    # 按行切
    # 数组有4行,生成4个布尔元素的数组
    ar_row = np.array([False, True, False, True])
    np_brr = np_arr[ar_row]
    print(np_brr)
    # [[ 6  7  8  9 10 11]
    #  [18 19 20 21 22 23]]
    
    # 按列切
    # 数组有6列,生成6个布尔元素的数组
    ar_column = np.array([True, True, False, True, False, True])
    # 所有行,1,2,4,6列
    # np_crr = np_arr[..., ar_column]
    np_crr = np_arr[:, ar_column]
    print(np_crr)
    # [[ 0  1  3  5]
    #  [ 6  7  9 11]
    #  [12 13 15 17]
    #  [18 19 21 23]]
    
    # 按布尔数组切(测试了报错)
    np_arr = np.arange(10).reshape(2, 5)
    print(np_arr)
    # [[0 1 2 3 4]
    #  [5 6 7 8 9]]
    
    # ar_row = np.array([0, 0, 1, 1])
    # ar_col = np.array([1, 3, 2, 4])
    # print(np_arr[ar_row, ar_col])  # --> [1 3 7 9]
    
    ar_row = np.array([True, True])
    ar_col = np.array([False, True, False, True, True])
    
    print(np_arr[ar_row, ar_col])
    
    Traceback (most recent call last):
      File "F:\StudyCode\CommonModule\003_NumPy\003_Numpy切片操作.py", line 405, in <module>
        print(np_arr[ar_row, ar_col])
    IndexError: shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (3,) 
    
  • 示例6:获取数组中 1、3、5、7、9行,2,4列的数据

    import numpy as np
    
    np_arr = np.arange(50).reshape(10, 5)
    print(np_arr)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]
    #  [20 21 22 23 24]
    #  [25 26 27 28 29]
    #  [30 31 32 33 34]
    #  [35 36 37 38 39]
    #  [40 41 42 43 44]
    #  [45 46 47 48 49]]
    
    # 获取 1、3、5、7、9行,2,4列的数据
    
    np_brr = np_arr[[0, 0, 2, 2, 4, 4, 6, 6, 8, 8], [1, 3, 1, 3, 1, 3, 1, 3, 1, 3]]
    
    print(np_brr)  # --->[ 1  3 11 13 21 23 31 33 41 43]
    
    ar_row = np.array([True, False, True, False, True, False, True, False, True, False])
    ar_col = np.array([False, True, False, True, False])
    # 先按行取
    temp = np_arr[ar_row]
    # 再按列取
    np_crr = temp[:, ar_col]
    
    # 合并
    np_crr = np_arr[ar_row][:, ar_col]
    # [[ 1  3]
    #  [11 13]
    #  [21 23]
    #  [31 33]
    #  [41 43]]
    

广播机制
  • 概念

  • 在NumPy中,广播(Broadcasting)是一种机制,用于在算术运算中处理不同形状的数组。当进行运算时,NumPy会自动地扩展较小数组以匹配较大数组的形状。这种机制让我们能够对不同形状的数组进行各种运算,而不需要手动填充数组以匹配形状

    • 如果两个数组a和b形状相同,即满足a.shape==b.shape,那么a * b的结果就是a与b数组对应位相乘。这要求维数相同,且各维度的长度相同
      import numpy as np
      
      np_arr = np.array([10, 20, 30, 40])
      np_brr = np.array([20, 30, 40, 50])
      
      print(np_arr + np_brr)      # ---> [30, 50, 70, 90]
      print(np_arr * np_brr)      # ---> [200, 600, 1200, 2000]
      
    • 两个形状不同的数组进行运算,广播机制会自动地扩展较小数组以匹配较大数组的形状
      import numpy as np
      
      np_arr = np.array([1, 2, 3])
      # [1, 2, 3]
      np_brr = np.arange(10,100,10).reshape(3, 3)
      # [[10 20 30]
      #  [40 50 60]
      #  [70 80 90]]
      
      print(np_arr + np_brr)
      # [[11 22 33]
      #  [41 52 63]
      #  [71 82 93]]
      
      
      • 在这里插入图片描述
  • 注意事项

    • 在NumPy中,广播机制主要用于读取、修改数组的元素,而不是用于写入数据。如果尝试通过广播机制修改数组的某些元素,可能会导致不可预见的结果或错误
  • 广播的规则:

    • 让进行运算的数组都向其中形状最长的数组看齐
    • 运算结果数组的形状是运算数组形状的各个维度上的最大值
    • 当运算数组在某个维度长度不同,且长度较小的数组长度大于1时,运算就会报错
  • 广播机制示例

  • 数组轴

    • 在这里插入图片描述
  • 示例1

    import numpy as np
    
    arr_a = np.arange(10, 100, 10).reshape(3, 3)
    print(arr_a)
    # [[10 20 30]
    #  [40 50 60]
    #  [70 80 90]]
    
    arr_b = np.array([1])
    print(arr_b)
    # [1]
    
    result = arr_a + arr_b
    print(result)
    # [[11 21 31]
    #  [41 51 61]
    #  [71 81 91]]
    
  • 图解

    • 在这里插入图片描述
  • 分析

    # arr_b在axis0和axis1两个维度的长度都小于arr_a
    # 但是arr_b的 axis0 和 axis1 的长度都是1
    # 所以arr_a和arr_b可以进行运算
    # 通过广播机制,会将arr_b的 axis0 和 axis1 都向arr_a看齐
    # 在arr_b的 axis0 和 axis1 方向无限制的复制自己,直到与arr_a长度一致
    # arr_b的 axis0 和 axis1 方向的第一个元素都是 1,所以全部填充1
    
  • 示例2

    import numpy as np
    
    arr_a = np.arange(10, 130, 10).reshape(4, 3)
    # print(arr_a)
    # [[ 10  20  30]
    #  [ 40  50  60]
    #  [ 70  80  90]
    #  [100 110 120]]
    arr_b = np.arange(1, 4, 1)
    # print(arr_b)
    # [1 2 3]
    
    result = arr_a + arr_b
    print(result)
    # [[ 11  22  33]
    #  [ 41  52  63]
    #  [ 71  82  93]
    #  [101 112 123]]
    
  • 图解

    • 在这里插入图片描述
  • 分析

    # arr_b在 axis1 与arr_a一致,在 axis0 长度小于arr_a
    # arr_b在 axis0 的长度为1,可以进行广播机制
    # arr_b在 axis0 方向无限制复制自身,直到与arr_a的axis0长度一致
    
  • 示例3

    import numpy as np
    
    arr_a = np.arange(10, 130, 30).reshape(4, 1)
    # print(arr_a)
    # [[ 10]
    #  [ 40]
    #  [ 70]
    #  [100]]
    
    arr_b = np.arange(1, 4)
    # print(arr_b)
    # [1 2 3]
    
    result = arr_a + arr_b
    print(result)
    # [[ 11  12  13]
    #  [ 41  42  43]
    #  [ 71  72  73]
    #  [101 102 103]]
    
  • 图解

    • 在这里插入图片描述
  • 分析

    # arr_a 与 arr_b 在 axis0 和 axis1 的长度都不一致
    # arr_b 在 axis0 的长度小于 arr_a,且 arr_b 的axis0长度为1
    # arr_a 在 axis1 的长度小于 arr_b,且 arr_a 的axis1长度为1
    # arr_b在axis0看齐arr_a,arr_a在axis1看齐arr_b
    
  • 示例4

    import numpy as np
    
    arr_a = np.arange(10, 130, 10).reshape(4, 3)
    # print(arr_a)
    # [[ 10  20  30]
    #  [ 40  50  60]
    #  [ 70  80  90]
    #  [100 110 120]]
    
    arr_b = np.arange(1, 7).reshape(2, 3)
    print(arr_b)
    # [[1 2 3]
    #  [4 5 6]]
    
    result = arr_a + arr_b
    print(result)
    
    # 报错
    result = arr_a + arr_b
    ValueError: operands could not be broadcast together with shapes (4,3) (2,3) 
    
  • 图解

    • 在这里插入图片描述
  • 分析

    # arr_a与arr_b在axis0的长度不一致
    # arr_b在axis0的长度小于arr_a,但是arr_b在axis0的长度不为1,所以不能进行广播
    # 运算则报错
    
  • 示例5

    import numpy as np
    
    arr_a = np.arange(10, 90, 10).reshape(4, 2)
    # print(arr_a)
    # [[10 20]
    #  [30 40]
    #  [50 60]
    #  [70 80]]
    
    arr_b = np.arange(1, 13).reshape(4, 3)
    # print(arr_b)
    # [[ 1  2  3]
    #  [ 4  5  6]
    #  [ 7  8  9]
    #  [10 11 12]]
    
    result = arr_a + arr_b
    print(result)
    
    # 报错
    result = arr_a + arr_b
    ValueError: operands could not be broadcast together with shapes (4,2) (4,3) 
    
  • 图解

    • 在这里插入图片描述
  • 分析

    # arr_a 与 arr_b 在axis1 方向的长度不一致
    # arr_a 的 axis1 长度小于arr_b,但是arr_a的axis1长度不为1,不能进行广播
    # 运算报错
    
Numpy常用方法
常用方法
方法说明语法
sum()求和np.sum(arr)
max()最大值np.max(arr)
min()最小值np.min(arr)
mean()平均值np.mean(arr)
arr.mean(axis)
median()中位数np.median(arr)
std()标准差np.std(arr)
var()方差np.var(arr)
average()加权平均值np.average(arr)
常用方法详解
  • 求和:sum()
    • 语法
      sum(a, axis=None, dtype=None, out=None, keepdims=np._NoValue, initial=np._NoValue, where=np._NoValue):
      
    • 示例
      arr_a = np.arange(1, 21).reshape(5, 4)
      # print(arr_a)
      # [[ 1  2  3  4]
      #  [ 5  6  7  8]
      #  [ 9 10 11 12]
      #  [13 14 15 16]
      #  [17 18 19 20]]
      
      print(np.sum(arr_a))            # ---> 210
      print(np.sum(arr_a, axis=1))    # ---> [10 26 42 58 74]
      print(np.sum(arr_a, axis=0))    # ---> [45 50 55 60]
      
  • 最大值:max()
    • 语法
      max(a, axis=None, out=None, keepdims=np._NoValue, initial=np._NoValue, where=np._NoValue)
      
    • 示例
      import numpy as np
      
      arr_a = np.array([2,34,4,7,9,32,12,22,6,21]).reshape(2, 5)
      print(arr_a)
      # [[ 2 34  4  7  9]
      #  [32 12 22  6 21]]
      
      print(np.max(arr_a))            # ---> 34
      print(np.max(arr_a, axis=0))    # ---> [32 34 22  7 21]
      print(np.max(arr_a, axis=1))    # ---> [34 32]    
      
  • 最小值:min()
    • 语法
      min(a, axis=None, out=None, keepdims=np._NoValue, initial=np._NoValue, where=np._NoValue)
      
    • 示例
      import numpy as np
      
      arr_a = np.array([2, 34, 4, 7, 9, 32, 12, 22, 6, 21]).reshape(2, 5)
      print(arr_a)
      # [[ 2 34  4  7  9]
      #  [32 12 22  6 21]]
      
      print(np.min(arr_a))            # ---> 2
      print(np.min(arr_a, axis=0))  # ---> [ 2 12  4  6  9]
      print(np.min(arr_a, axis=1))  # ---> [2 6]
      
  • 平均值:mean()
    • 获取指定轴上的平均值
    • 语法
      mean(a, axis=None, dtype=None, out=None, keepdims=np._NoValue, *,where=np._NoValue):
      
    • 示例
      import numpy as np
      
      arr_a = np.arange(20).reshape(4, 5)
      print(arr_a)
      # [[ 0  1  2  3  4]
      #  [ 5  6  7  8  9]
      #  [10 11 12 13 14]
      #  [15 16 17 18 19]]
      
      # 获取整个数组的平均值
      print(arr_a.mean())             # ---> 9.5
      
      # 获取axis0方向(纵向)每一列的平均值
      print(arr_a.mean(axis=0))       # ---> [ 7.5  8.5  9.5 10.5 11.5]
      
      # 获取axis1方向(横向)每一行的平均值
      print(arr_a.mean(axis=1))       # ---> [ 2.  7. 12. 17.]
      
  • 中位数:median()
    • 中位数:是按照顺序排列的一组数据中局域中间位置的数
    • 语法
      median(a, axis=None, out=None, overwrite_input=False, keepdims=False)
      
    • 示例
      import numpy as np
      
      arr = np.array([1, 7, 9, 6, 3])
      print(arr)
      # [1, 7, 9, 6, 3]
      
      print(np.median(arr))           # ---> 6.0
      # 先排序,[1, 3, 6, 7, 9]
      # 取中位数:6
      
      brr = np.array([1, 7, 9, 6, 3, 4])
      print(brr)
      # [1 7 9 6 3 4]
      
      print(np.median(brr))           # ---> 5.0
      # 先排序,[1, 3, 4, 6, 7, 9]
      # 取中位数:(4 + 6)/2
      
  • 方差:var()
    • 方差越小,代表这组数据越稳定
    • 方差越大,代表这组数据越不稳定
    • 计算方式
      1. 数组arr_a中每一个数值 减去 数组平均值,生成一个新数组arr_b
      2. 新数组arr_b中每一个数值的平方,再除以数组的元素个数,生成新数组 arr_c
      3. 对新数组 arr_c 的数值进行汇总求和
      
      import numpy as np
      
      result = np.sum(((arr_a - np.mean(arr_a))**2)/arr_a.size)
      
      
    • 语法
      var(a, axis=None, dtype=None, out=None, ddof=0, keepdims=np._NoValue, *, where=np._NoValue):
      
    • 示例
      import numpy as np
      
      arr_a = np.array([60, 75, 83, 57, 95, 99])
      arr_b = np.array([70, 75, 73, 87, 85, 79])
      
      print(np.var(arr_a))            # ---> 254.80555555555554
      print(np.var(arr_b))            # ---> 38.138888888888886    
      
  • 标准差:std()
    • 标准差是表征被统计数据组中,每一数据偏离平均值程度大小的数量指标。亦称“均方差”或“均方根”
    • 标准差是方差的算术平方根(方差开平方根)
    • 标准差越大,代表大部分数值和平均值之间的差异越大,反之差异越小
    • 标准差应用于投资上,可作为量度回报稳定性的指标
      • 标准差数值越大,代表回报远离过去平均数值,回报不稳定,风险越高
      • 标准差数值越小,代表回报较为稳定,风险越小
    • 计算方式
      1. 数组arr_a中每一个数值 减去 数组平均值,生成一个新数组arr_b
      2. 新数组arr_b中每一个数值的平方,再除以数组的元素个数,生成新数组 arr_c
      3. 对新数组 arr_c 的数值进行汇总求和
      4. 对求和后的数值开平方根得到的结果就是方差
      
      import math
      import numpy as np
      
      math.sqrt(np.sum(((arr_a - np.mean(arr_a))**2)/arr_a.size))
      
      # math.sqrt()   开平方根
      
    • 语法
      std(a, axis=None, dtype=None, out=None, ddof=0, keepdims=np._NoValue, *, where=np._NoValue):
      
    • 示例
      import numpy as np
      
      arr_a = np.array([60, 75, 83, 57, 95, 99])
      arr_b = np.array([70, 75, 73, 87, 85, 79])
      
      print(np.std(arr_a))            # ---> 15.962629969887654
      print(np.std(arr_b))            # ---> 6.175669104549635    
      
  • 加权平均值:average()
    • 在加权平均中,每个数据点都有一个对应的权重值,该权重值决定了数据点在计算平均值时的重要程度
    • 通过相乘各个数据点的值与权重值,并将结果求和后再除以所有权重值的总和,就可以得到加权平均值
      # 例如:在评分中,专家、老师和学生的权重为:0.5 : 0.3 : 0.2
      # 就某观点,满分10分的情况下,专家打8分,老师打7分,学生打6分
      
      # 计算平均值
      (8 + 7 + 6) / 3 = 7
      
      # 计算加权平均值
      8 * 0.5 + 7 * 0.3 + 6 * 0.2 = 7.3
      
    • 语法
      average(a, axis=None, weights=None, returned=False, *, keepdims=np._NoValue)
      
      # weights:权重占比数组
      
    • 示例1
      # 在评分中,专家、老师和学生的权重为:0.5 : 0.3 : 0.2
      # 就某观点,满分10分的情况下,专家打8分,老师打7分,学生打6分
      
      import numpy as np
      
      arr_a = np.array([8, 7, 6])
      arr_b = np.array([0.5, 0.3, 0.2])
      
      # 平均值
      print('平均值:', np.mean(arr_a))
      print('加权平均值:', np.average(arr_a, weights=arr_b))
      
      # 平均值: 7.0
      # 加权平均值: 7.3
      
    • 示例2
      # 求学生的总成绩
      # 各科成绩折算率
          # 语文、数学、英语:100%
          # 生物、地理:30%
          # 历史:40%
          # 政治:70%
          
      import numpy as np
      
      # 各科成绩折算率:语文、数学、英语:100%、 生物、地理:30%、 历史:40%、 政治:70%
      zhanbi = np.array([1, 1, 1, 0.3, 0.3, 0.4, 0.7])
      
      # 班级人员成绩
      # 语文、数学、英语、生物、地理、历史、政治
      zhangsan = np.array([106, 111, 95, 100, 89, 75, 71])
      wangwu = np.array([101, 116, 100, 70, 72, 89, 95])
      lisi = np.array([103, 92, 60, 74, 62, 75, 91])
      zhaoliu = np.array([106, 84, 63, 99, 87, 83, 65])
      zhouheng = np.array([69, 101, 69, 81, 95, 79, 64])
      wangcan = np.array([73, 115, 90, 87, 67, 75, 78])
      tiancai = np.array([72, 104, 92, 86, 76, 78, 77])
      
      
      cj = np.array([zhangsan, wangwu, lisi, zhaoliu, zhouheng, wangcan, tiancai])
      
      print(np.sum(cj, axis=1))
      # 人员:[zhangsan, wangwu, lisi, zhaoliu, zhouheng, wangcan, tiancai]
      # 总分:[647 643 557 587 558 585 585]
      # 排名:1, 2, 7, 3, 6, 4, 4
      
      print(np.sum(cj * zhanbi, axis=1))
      # 人员:[zhangsan, wangwu, lisi, zhaoliu, zhouheng, wangcan, tiancai]
      # 加权总分:[448.4 461.7 389.5 387.5 368.2 408.8 401.7]
      # 排名:2, 1, 5, 6, 7, 3, 4    
      

random模块
常用方法
方法说明语法
random.rand()生成[0,1)均匀分布随机数数组random.rand(x [,y [,z]])
random.randn()生成标准正态分布随机数数组random.randn(x [,y [,z]])
random.normal()生成非标准正态分布随机数数组random.normal(loc,scale,size)
random.randint()生随机整数数组random.randint(low [,hight,size,dtype])
random.sample()生成[0,1)的随机浮点数数组random.sample(size)
random.random()生成[0,1)的随机浮点数数组random.random(size)
random.seen()设置随机数生成器种子random.seed(seed=None)
方法详解
  • 生成[0, 1)随机数:rand

    • 根据指定维度生成[0,1)之间的均匀分布随机数据,含0,不含1
    • 通过参数个数确定生成数组的秩数(…,块, 行, 列)
    • 语法
      numpy.random.rand(int1 [,int2 [,int3]])
      
    • 示例
      import numpy as np
      
      # 生成一维随机数组:4个元素
      a = np.random.rand(4)
      print(a)
      # [0.7557538  0.95891308 0.92564094 0.40087449]
      
      # 生成二维随机数组:4行2列
      b = np.random.rand(4, 2)
      print(b)
      # [[0.00319582 0.15745129]
      #  [0.34666311 0.1090695 ]
      #  [0.2699511  0.97655925]
      #  [0.1121586  0.29664613]]
      
      # 生成三维随机数组:4块2行3列
      c = np.random.rand(4, 2, 3)
      print(c)
      # [[[0.24553028 0.06080189 0.79558608]
      #   [0.15551388 0.16026187 0.31865016]]
      #
      #  [[0.03547529 0.99929734 0.97370055]
      #   [0.38092348 0.02374626 0.50931851]]
      #
      #  [[0.99630069 0.20782222 0.37857884]
      #   [0.29318473 0.59264743 0.69834764]]
      #
      #  [[0.44172721 0.68281501 0.3876927 ]
      #   [0.7007537  0.46816175 0.73113837]]]
      
  • 生成标准正态分布数组:randn

    • 根据指定维度生成标准正态分布随机数据的数组
    • 通过参数个数确定生成数组的秩数(…,块, 行, 列)
    • 标准正态分布:又称为u分布,是以0为均数、以1为标准差的正态分布,记为N(0,1)
    • 语法
      numpy.random.randn(int1 [,int2 [,int3]])
      
    • 语法
    • 示例
      import numpy as np
      
      # 生成一维标准正态分布随机数:4列
      a = np.random.randn(4)
      print(a)
      # [-0.72976138 -0.57480782 -0.70765959 -2.03272241]
      
      # 生成二维标准正态分布随机数:4行2列
      b = np.random.randn(4, 2)
      print(b)
      # [[ 0.34644317  1.12548764]
      #  [ 1.60157572 -1.35348353]
      #  [ 1.55494193  3.45449688]
      #  [ 0.40454881 -0.64048287]]
      
      # 生成三维标准正态分布随机数:4块2行3列
      c = np.random.randn(4, 2, 3)
      print(c)
      # [[[ 0.53612457  0.37905229 -0.79143632]
      #   [ 0.5674659  -0.90537111  0.60493321]]
      # 
      #  [[ 0.50802307  0.28369539 -0.67810582]
      #   [-0.60829232  2.10216324 -1.68871128]]
      # 
      #  [[ 0.09004208  0.69930548  0.30566251]
      #   [-0.07676095  0.93235622  0.32499444]]
      # 
      #  [[-0.3466686   2.05014758  0.27562   ]
      #   [ 0.46559955 -0.35983169  0.12782258]]]
      
  • 生成非标准正态随机数:normal

    • 用于生成服从正态分布(高斯分布)的随机数的方法
    • 生成的随机数服从均值为 loc,标准差为 scale 的正态分布。
    • 默认情况下,loc 和 scale 均为 0,生成符合标准正态分布的随机数
    • 语法
      numpy.random.normal(loc=0.0, scale=1.0, size=None)
      
    • 示例
      import numpy as np
      
      a = np.random.normal(5, 3, 5)
      print(a)
      # [4.47495308 4.66880493 3.15194175 3.86639833 4.9994928 ]
      
      b = np.random.normal(5, 3, (2,5))
      print(b)
      # [[12.16631503  4.3196272   1.3928081   4.31908768  7.43865449]
      #  [11.63966175  6.34903714  4.52020119  4.60970105  2.86709677]]    
      
  • 生成随机整数:randint

    • 生成指定范围内一个或一组随机整数
    • 语法
      numpy.random.randint(low, high=None, size=None, dtype=None)
      
      # 参数说明
          # low       # 整数或整数形式的数组,最小值(包含)
          # high      # 整数或整数形式的数组,最大值(不包含)
          # size      # 整数或者整数元组,数组秩数与维度大小(元素个数)
                      # size = 4          一维,4个元素
                      # size = (2, 4)     二维,4行2列
                      # size = (2, 3, 4)  三维,2块3行4列
          # dtype     # 数据类型,默认是np.int
          
      # high没填写时,默认生成随机数的范围是[0, low)
      
    • 示例
      import numpy as np
      
      # 指定low参数:生成一个0~low之间的随机整数
      a = np.random.randint(low=5)
      print(a)    # ---> 2
      
      # 指定low参数和high参数:生成一个low~high之间的随机整数
      b = np.random.randint(low=1, high=8)
      print(b)    # ---> 1
      
      # 指定size参数:size元素个数控制数组秩数,元素大小控制维度大小
      # 生成一维数组
      c = np.random.randint(low=1, high=8, size=3)
      print(c)    # ---> [7 2 7]
      
      # 生成二维数组
      d = np.random.randint(low=1, high=8, size=(2, 3))
      print(d)
      # [[2 1 1]
      #  [1 2 3]]
      
      # 生成三维数组
      e = np.random.randint(low=1, high=8, size=(2, 3, 4))
      print(e)
      # [[[7 2 5 1]
      #   [6 2 7 2]
      #   [1 1 4 1]]
      #
      #  [[6 3 5 2]
      #   [6 5 1 7]
      #   [4 6 6 6]]]
      
      # 指定dtype参数
      f1 = np.random.randint(low=-10, high=-1, size=(2, 3))
      print(f1)
      # [[-9 -4 -9]
      #  [-4 -8 -2]]
      
      # uint8:无符号整数
      f2 = np.random.randint(low=-10, high=-1, size=(2, 3), dtype=np.uint8)
      print(f2)
      # 报错:low is out of bounds for uint8(对于uint8, Low是越界的)
      
      # 高级用法
      # 生成三个最小分别为2,4,6、最大不超过10的值
      a = np.random.randint(low=[2, 4, 6], high=10)
      print(a)    # ---> [7 4 8]
      
      # 生成三个最小为1,最大分别不超过2,8,15的值
      b = np.random.randint(low=1,high=[2,8,15])
      print(b)    # ---> [ 1  5 13]
      
      # 生成三个最小分别为1,8,10、最大分别为10,20,30的值
      c = np.random.randint([1, 8, 10], [10, 20, 30])
      print(c)    # ---> [ 7 13 20]
      
      # 生成3*4数组,每列最小值分别为1,3,5,7、每行最大值分别为20,40,60
      # 广播机制得到每一个元素的最大最小值
      # [1,20) [3,20) [5,20) [7,20)
      # [1,40) [3,40) [5,40) [7,40)
      # [1,60) [3,60) [5,60) [7,60)
      
      d = np.random.randint([1, 3, 5, 7], [[20], [40], [60]])
      print(d)
      # [[13  7 18 17]
      #  [25 32 33 39]
      #  [54  5 22 34]]
      
      # 生成4*3数组,每行最小值分别为1,3,5,18、每列最大值分别为20,40,60
      # 广播机制得到每一个元素的最大最小值
      # [1,20) [1,40) [1,60)
      # [3,20) [3,40) [3,60)
      # [5,20) [5,40) [5,60)
      # [18,20) [18,40) [18,60)
      e = np.random.randint([[1], [3], [5], [18]], [20, 40, 60])
      print(e)
      # [[ 8 12 48]
      #  [10 20 20]
      #  [ 5 29 27]
      #  [19 19 47]]
      
      • 在这里插入图片描述
  • 生成随机浮点数:sample

    • 生成[0,1)范围内一个或一组随机浮点数
    • 语法
      numpy.random.sample(size=None)
      
    • 示例
      import numpy as np
      
      # 无参数,生成一个[0,1)范围的随机浮点数
      a = np.random.sample()
      print(a)
      # 0.695289644245854
      
      # 一个参数,生成一组1行3列[0,1)范围的随机浮点数
      b = np.random.sample(3)
      print(b)
      # [0.80919477 0.48353012 0.95753225]
      
      # 一个2个元素的元组参数,生成一组2行4列[0,1)范围的随机浮点数
      c = np.random.sample((2, 4))
      print(c)
      # [[0.61145673 0.80925237 0.83446519 0.69341159]
      #  [0.61430661 0.29907036 0.63042283 0.53730137]]
      
      # 一个3个元素的元组参数,生成一组2块4行3列[0,1)范围的随机浮点数
      d = np.random.sample((2, 4, 3))
      print(d)
      # [[[0.44394489 0.76176051 0.82075338]
      #   [0.5524654  0.13637014 0.46931171]
      #   [0.7488215  0.62866061 0.69508182]
      #   [0.38084954 0.99252675 0.23984405]]
      # 
      #  [[0.44758257 0.84448671 0.76684157]
      #   [0.8688737  0.78412187 0.50162363]
      #   [0.82565943 0.22938796 0.19664344]
      #   [0.50370824 0.84622079 0.39960914]]]
      
  • 生成随机浮点数:random

    • 生成一个在[0, 1)范围内的随机浮点数
    • 语法
      numpy.random.random(size=None)
      
    • 示例
      import numpy as np
      
      # 无参数,生成一个[0,1)范围的随机浮点数
      a = np.random.random()
      print(a)
      # 0.5997276941356183
      
      # 一个参数,生成一组1行3列[0,1)范围的随机浮点数
      b = np.random.random(3)
      print(b)
      # [0.26123669 0.95622154 0.90114394]
      
      # 一个2个元素的元组参数,生成一组2行4列[0,1)范围的随机浮点数
      c = np.random.random((2, 4))
      print(c)
      # [[0.13418736 0.5284547  0.21783092 0.55466155]
      #  [0.82305416 0.47990057 0.37019661 0.56089833]]
      
      # 一个3个元素的元组参数,生成一组2块4行3列[0,1)范围的随机浮点数
      d = np.random.random((2, 4, 3))
      print(d)
      # [[[0.09541319 0.82741157 0.64856836]
      #   [0.63802073 0.06620751 0.81025966]
      #   [0.98665942 0.91619257 0.85657233]
      #   [0.24114507 0.2738937  0.51147226]]
      # 
      #  [[0.6152128  0.51657019 0.69920683]
      #   [0.10127236 0.05260505 0.21725041]
      #   [0.38288493 0.83852435 0.99830059]
      #   [0.03973    0.74731502 0.25342351]]]
      
    • np.random.random()np.random.sample()在NumPy库中都是用于生成[0, 1)范围内的随机浮点数的函数。它们在功能上是等价的,但在命名和文档描述上有所不同。
    • 在实际应用中,推荐使用np.random.random()来生成随机数,因为它已经被广泛接受并且更加符合NumPy的命名规范
  • 设置随机数生成器种子:seed

    • 使用相同的seed()值时,每次生成的随机数都相同,使得随机数可以预测
    • 使用seed()函数设置一次随机种子,并不能让后续所有的随机函数生成一样的随机数
    • 需要每次使用随机函数之前都调用seed()函数,并设置相同的随机种子,才可以让随机函数生成的随机数相同
    • 语法
      numpy.random.seed(seed=None)
      
    • 示例
      import numpy as np
      
      # 调用一次seed()函数设置随机种子,并不能让后续的随机函数生成的随机数一致
      np.random.seed(1)
      a = np.random.randint(1, 15, size=5)
      print(a)    # ---> [ 6 12 13  9 10]
      
      b = np.random.randint(1, 15, size=5)
      print(b)    # ---> [12  6  1  1  2]
      
      # 每次调用随机函数之前都调用一次seed()函数,并设置相同的随机种子,才能让后续的随机函数生成的随机数一致
      np.random.seed(1)
      a = np.random.randint(1, 15, size=5)
      print(a)    # ---> [ 6 12 13  9 10]
      
      np.random.seed(1)
      b = np.random.randint(1, 15, size=5)
      print(b)    # ---> [ 6 12 13  9 10]
      
      
      # 每次调用随机函数之前都调用一次seed()函数,并设置不同的随机种子,不能让后续的随机函数生成的随机数一致
      np.random.seed(1)
      a = np.random.randint(1, 15, size=5)
      print(a)    # ---> [ 6 12 13  9 10]
      
      np.random.seed(2)
      b = np.random.randint(1, 15, size=5)
      print(b)    # ---> [ 9 14  9  7 12]
      
      

其他函数
方法说明语法
resize()生成指定形状的新数组np.resize(arr,new_shape)
append()将元素添加到指定数组的末尾append(arr, values, axis=None)
insert()沿着规定的轴将元素插入到指定的元素前insert(arr, obj, values, axis=None)
delete()删除某个轴上的子数组,并返回删除后的新数组delete(arr, obj, axis=None)
unique()用于删除数组中重复的元素,并按元素由大到小排序生成一个新数组unique(ar, return_index=False, return_inverse=False,
       return_counts=False, axis=None, *, equal_nan=True) |

| sort() | 对数组进行排序,返回一个数组副本 | |
| argsort() | 沿着指定的轴,对数组的元素进行排序,并返回排序后的元素索引数组 | argsort(a, axis=-1, kind=None, order=None) |
| argwhere() | 返回数组内符合条件的元素的索引值 | argwhere(a) |
| argmax() | 沿着指定的轴,返回最大值 | argmax(a, axis=None, out=None, *, keepdims=np._NoValue) |
| argmin() | 沿着指定的轴,返回最小值 | argmin(a, axis=None, out=None, *, keepdims=np._NoValue) |

其他函数详解
  • 按原数组元素生成指定维度新数组:resize
    • 语法
      numpy.resize(a, new_shape)
      
    • 示例
      import numpy as np
      
      # 原数组
      a = np.arange(10).reshape(2,5)
      print(a)
      # [[0 1 2 3 4]
      #  [5 6 7 8 9]]
      
      # 根据原数组元素生成指定维度新数组
      b = np.resize(a, (5,2))
      print(b)
      # [[0 1]
      #  [2 3]
      #  [4 5]
      #  [6 7]
      #  [8 9]]
      
      # 当原数组元素个数不够时,会先将原数组元素排列完毕
      # 再从原数组元素开头位置开始复制元素
      c = np.resize(a, (5, 3))
      print(c)
      # [[0 1 2]
      #  [3 4 5]
      #  [6 7 8]
      #  [9 0 1]
      #  [2 3 4]]
      
      # ===================================================
      # 数组对象也有一个resize方法可以修改数组维度
      # 当元素不够时,设置refcheck参数为True,会用0补全
      # 但是,当数组使用过reshape方法调整过维度,再用ndarray.resize调整时,会报错
      a = np.arange(20)
      print('a:', a)
      # a: [ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19]
      
      b = np.arange(20).reshape(4, 5)
      print('b:', b)
      # b: [[ 0  1  2  3  4]
      #  [ 5  6  7  8  9]
      #  [10 11 12 13 14]
      #  [15 16 17 18 19]]
      
      print('-' * 20)
      
      a.resize((3, 10), refcheck=True)
      print('a:', a)
      # a: [[ 0  1  2  3  4  5  6  7  8  9]
      #  [10 11 12 13 14 15 16 17 18 19]
      #  [ 0  0  0  0  0  0  0  0  0  0]]
      
      b.resize((3, 10), refcheck=True)
      print('b:', b)
      # 报错:cannot resize this array: it does not own its data
      
  • 添加元素到末尾:append
    • 将一个元素或者一个数组中的元素添加到原数组的末尾,默认返回一个一维数组
    • 语法
      numpy.append(arr, values, axis=None)
      
      # 参数详解
          # arr:原数组
          # values:要添加的元素或包含元素的数组
          # axis:指定将元素添加到原数组的那个秩方向
      
      # 当axis=0时,元素数组的维度必须与原数组维度一致,且元素数组每一行长度必须与原数组长度一致
      # 当axis=1时,元素数组的维度必须与原数组维度一致,且元素数组的行数必须与原数组行数一致
      
    • 示例
      import numpy as np
      
      a = np.arange(10).reshape(2, 5)
      print(a)
      # [[0 1 2 3 4]
      #  [5 6 7 8 9]]
      
      # 不设置axis参数,直接添加元素,结果是一维数组
      b = np.append(a, 100)
      print(b)
      # [  0   1   2   3   4   5   6   7   8   9 100]
      
      # b = np.append(a, [100,101,102])
      # print(b)
      # # [  0   1   2   3   4   5   6   7   8   9 100 101 102]
      
      # # 设置axis参数为0,在axis=0方向扩展追加元素(纵向增加N行)
      # # 注:
      # # # 1. 元素数组的维度必须与原数组维度一致
      # # # 2. 元素数组每一行长度必须与原数组长度一致
      c = np.append(a, [[200, 201, 202, 203, 204],[300, 301, 302, 303, 304]], axis=0)
      print(c)
      # [[  0   1   2   3   4]
      #  [  5   6   7   8   9]
      #  [200 201 202 203 204]
      #  [300 301 302 303 304]]
      
      # 设置axis参数为1,在axis=1方向扩展追加元素(横向每一行增加N列)
      # 注:
      # # 1. 元素数组的维度必须与原数组维度一致
      # # 2. 元素数组行数必须与原数组行数一致
      d = np.append(a, [[200, 201], [300,301]], axis=1)
      print(d)
      # [[  0   1   2   3   4 200 201]
      #  [  5   6   7   8   9 300 301]]
      
  • 插入元素到指定位置:insert
  • 沿指定轴方向,将元素插入到制定索引值的位置(原索引位置上的元素往后移)
  • 如果没有指定轴方向,则返回一个一维数组
    • 语法
      numpy.insert(arr, obj, values, axis=None)
      
      # 参数详解
          # arr:原数组
          # obj:指定索引位置
          # values:需要插入的元素
          # axis:指定轴方向
      
      # 当axis=0时
          # 1. 如果插入的元素为单个值,则会复制当前元素填充到与原数组的axis=1方向长度一致
          # 2. 如果插入的元素为多个值,则数组在axis=1方向的长度必须与原数组在axis=1方向的长度一致(元素数组的列数要与原数组的列数一致)
      
      # 当axis=1时
          # 1. 如果插入的元素为单个值,则会在原数组的每一行的指定索引位置插入当前元素值
          # 2. 如果插入的元素为多个值,则数组在axis=1方向的长度必须与原数组在axis=0方向的长度一致(元素数组的列数要与原数组的行数一致)
      
    • 示例
      import numpy as np
      
      a = np.arange(10).reshape(2, 5)
      print(a)
      # [[0 1 2 3 4]
      #  [5 6 7 8 9]]
      
      # 不指定axis参数,将原数组展开为一维,然后插入元素
      b1 = np.insert(a, 2, 100)
      print(b1)
      # [  0   1 100   2   3   4   5   6   7   8   9]
      
      b2 = np.insert(a, 2, [200, 201])
      print(b2)
      # [  0   1 200 201   2   3   4   5   6   7   8   9]
      
      # 指定axis参数为0,在axis=0方向指定索引位置插入元素(纵向插入N行)
      # 注意
      # # 1. 如果插入的元素为单个值,则会复制当前元素填充到与原数组的axis=1方向长度一致
      # # 2. 如果插入的元素为多个值时,则数组在axis=1方向的长度必须与原数组在axis=1方向的长度一致
      c1 = np.insert(a, 2, 100, axis=0)
      print(c1)
      # [[  0   1   2   3   4]
      #  [  5   6   7   8   9]
      #  [100 100 100 100 100]]
      
      c2 = np.insert(a, 2, [100], axis=0)
      print(c2)
      # [[  0   1   2   3   4]
      #  [  5   6   7   8   9]
      #  [100 100 100 100 100]]
      
      # 要插入元素的数组的列数必须与原数组的列数一致
      c3 = np.insert(a, 2, [100, 101, 102, 103, 104], axis=0)
      print(c3)
      # [[  0   1   2   3   4]
      #  [  5   6   7   8   9]
      #  [100 101 102 103 104]]
      
      c4 = np.insert(a, 1, [[100, 101, 102, 103, 104], [200, 201, 202, 203, 204]], axis=0)
      print(c4)
      # [[  0   1   2   3   4]
      #  [100 101 102 103 104]
      #  [200 201 202 203 204]
      #  [  5   6   7   8   9]]
      
      
      # 指定axis参数为1,在axis=1方向指定索引位置插入元素(横向插入N列)
      # 注意
      # # 1. 如果插入的元素为单个值,则会在原数组的每一行的指定索引位置插入当前元素值
      # # 2. 如果插入的元素为多个值,则数组在axis=1方向的长度必须与原数组在axis=0方向的长度一致
      d1 = np.insert(a, 1, 100, axis=1)
      print(d1)
      # [[  0 100   1   2   3   4]
      #  [  5 100   6   7   8   9]]
      
      d1 = np.insert(a, 1, [100], axis=1)
      print(d1)
      # [[  0 100   1   2   3   4]
      #  [  5 100   6   7   8   9]]
      
      
      # 要插入元素的数组列数必须与原数组的行数一致
      d2 = np.insert(a, 1, [200, 300], axis=1)
      print(d2)
      # [[  0 200   1   2   3   4]
      #  [  5 300   6   7   8   9]]
      
      # d3 = np.insert(a, 1, [200, 300, 400], axis=1)
      # print(d3)
      # 报错:could not broadcast input array from shape (3,1) into shape (2,1)
      
      # d3 = np.insert(a, 1, [200, 300, 400, 500], axis=1)
      # print(d3)
      # 报错:could not broadcast input array from shape (4,1) into shape (2,1)
      
      d5 = np.insert(a, 1, [[200, 201], [300, 301]], axis=1)
      print(d5)
      # [[  0 200 300   1   2   3   4]
      #  [  5 201 301   6   7   8   9]]
      
  • 删除指定索引位置的元素:delete
    • 沿指定轴方向,删除指定索引位置的元素
    • 语法
      numpy.delete(arr, obj, axis=None)
      
      # 参数详解
          # arr:原数组
          # obj:指定要删除的索引号
          # axis:指定轴方向
      
    • 示例
      import numpy as np
      
      a = np.arange(10, 30).reshape(4, 5)
      print(a)
      # [[10 11 12 13 14]
      #  [15 16 17 18 19]
      #  [20 21 22 23 24]
      #  [25 26 27 28 29]]
      
      # 不指定axis参数,会现将原数组展开成一维,再删除指定索引位置元素
      b1 = np.delete(a, 1)
      print(b1)
      # [10 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29]
      
      b2 = np.delete(a, [1])
      print(b2)
      # [10 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29]
      
      b3 = np.delete(a, [1, 3, 5, 7, 9])
      print(b3)
      # [10 12 14 16 18 20 21 22 23 24 25 26 27 28 29]
      
      # 指定axis参数为0,删除axis=0方向的元素
      # 整行删除
      c1 = np.delete(a, 1, axis=0)
      print(c1)
      # [[10 11 12 13 14]
      #  [20 21 22 23 24]
      #  [25 26 27 28 29]]
      
      c2 = np.delete(a, [1], axis=0)
      print(c2)
      # [[10 11 12 13 14]
      #  [20 21 22 23 24]
      #  [25 26 27 28 29]]
      
      c3 = np.delete(a, [1, 3], axis=0)
      print(c3)
      # [[10 11 12 13 14]
      #  [20 21 22 23 24]]
      
      c4 = np.delete(a, [[1, 3], [1, 2], [1, 2], [2, 3]], axis=0)
      # 个人理解相当于是
      # c4 = np.delete(a, [1, 3, 2], axis=0)
      print(c4)
      # [[10 11 12 13 14]]
      
      # 设置axis参数为1,删除axis=1方向的元素
      # 整列删除
      d1 = np.delete(a, 1, axis=1)
      print(d1)
      # [[10 12 13 14]
      #  [15 17 18 19]
      #  [20 22 23 24]
      #  [25 27 28 29]]
      
      d2 = np.delete(a, [1], axis=1)
      print(d2)
      # [[10 12 13 14]
      #  [15 17 18 19]
      #  [20 22 23 24]
      #  [25 27 28 29]]
      
      d3 = np.delete(a, [1, 2], axis=1)
      print(d3)
      # [[10 13 14]
      #  [15 18 19]
      #  [20 23 24]
      #  [25 28 29]]
      
      d4 = np.delete(a, [[1, 2], [1, 3], [1, 4], [1, 2]], axis=1)
      # 个人理解相当于
      # d4 = np.delete(a,[1, 2, 3, 4], axis=1)
      print(d4)
      # [[10 14]
      #  [15 19]
      #  [20 24]
      #  [25 29]]
      
  • 删除数组中重复的元素并排序:unique
    • 删除数组中重复的元素,并按元素由大到小排序生成一个新数组
    • 语法
      unique(ar, return_index=False, return_inverse=False, return_counts=False, axis=None, *, equal_nan=True)
      
      # 参数详解
          # ar:原数组
          # return_index:如果为True,则返回新数组元素在原数组中的索引位置
          # return_inverse:如果为True,则返回原数组元素在新数组中的索引位置
          # return_counts:如果为True,则返回去重后的数组元素在原数组中出现的次数
          # axis:
          # equal_nan:
      
    • 示例
      import numpy as np
      
      a = np.array([1, 3, 4, 2, 3, 4, 5, 6, 3, 4, 5, 6])
      print(a)
      # [1 3 4 2 3 4 5 6 3 4 5 6]
      
      # 不设置参数,获取去重后并且按升序排序后的新数组
      b1 = np.unique(a)
      print(b1)
      # [1 2 3 4 5 6]
      
      # return_index:如果为True,则返回新数组元素在原数组中的索引位置
      b2 = np.unique(a, return_index=True)
      print(b2)
      # (array([1, 2, 3, 4, 5, 6]), array([0, 3, 1, 2, 6, 7], dtype=int64))
      
      # return_inverse:如果为True,则返回原数组元素在新数组中的索引位置
      b3 = np.unique(a, return_inverse=True)
      print(b3)
      # (array([1, 2, 3, 4, 5, 6]), array([0, 2, 3, 1, 2, 3, 4, 5, 2, 3, 4, 5], dtype=int64))
      
      # return_counts:如果为True,则返回去重后的数组元素在原数组中出现的次数
      b4 = np.unique(a, return_counts=True)
      print(b4)
      # (array([1, 2, 3, 4, 5, 6]), array([1, 1, 3, 3, 2, 2], dtype=int64))
      
  • 对数组进行排序:sort
    • 对数组进行排序,返回一个数组副本
    • 语法
      numpy.sort(a, axis=-1, kind=None, order=None)
      
      # 参数详解
          # a:原数组
          # axis:指定轴方向进行排序,如果没有指定axis,默认在最后一个轴上排序
          # kind:默认为quicksort(快速排序)
          # order:若数组设置了字段,通过order可以设置按指定字段进行排序
      
    • 示例
      import numpy as np
      
      a = np.array([1, 3, 4, 2, 3, 4, 5, 6, 3, 4, 5, 6])
      print(a)
      # # [1 3 4 2 3 4 5 6 3 4 5 6]
      
      b1 = np.sort(a)
      print(b1)
      # # [1 2 3 3 3 4 4 4 5 5 6 6]
      
      a = a.reshape(6, 2)
      print(a)
      # [[1 3]
      #  [4 2]
      #  [3 4]
      #  [5 6]
      #  [3 4]
      #  [5 6]]
      
      # 设置axis参数为0,按axis=0轴方向进行排序
      b2 = np.sort(a, axis=0)
      print(b2)
      # [[1 2]
      #  [3 3]
      #  [3 4]
      #  [4 4]
      #  [5 6]
      #  [5 6]]
      
      # 设置axis参数为1,按axis=1轴方向进行排序
      b3 = np.sort(a, axis=1)
      print(b3)
      # [[1 3]
      #  [2 4]
      #  [3 4]
      #  [5 6]
      #  [3 4]
      #  [5 6]]
      
      # 设置order参数,按指定字段进行排序
      dt = np.dtype([('name','U4'),('age', int)])
      a = np.array([('张三', 20),('李四', 18),('王五', 22),('赵六',15),('周灿', 21)],dtype=dt)
      print(a)
      # [('张三', 20) ('李四', 18) ('王五', 22) ('赵六', 15) ('周灿', 21)]
      
      b4 = np.sort(a, order='age')
      print(b4)
      # [('赵六', 15) ('李四', 18) ('张三', 20) ('周灿', 21) ('王五', 22)]
      
  • 沿着指定的轴,对数组进行排序:argsort
    • 沿着指定的轴,对数组的元素进行排序,并返回排序后的元素索引数组
    • 语法
      numpy.argsort(a, axis=-1, kind=None, order=None)
      
      # 参数详解
          # a:原数组
          # axis:指定轴方向进行排序,如果没有指定axis,默认在最后一个轴上排序
          # kind:默认为quicksort(快速排序)
          # order:若数组设置了字段,通过order可以设置按指定字段进行排序
      
      
    • 示例
      import numpy as np
      
      a = np.array([[11, 15, 10, 22, 35],[41, 22, 13, 6, 16],[21, 5, 19, 32, 85],[21, 12, 33, 26, 56]])
      print(a)
      # [[11 15 10 22 35]
      #  [41 22 13  6 16]
      #  [21  5 19 32 85]
      #  [21 12 33 26 56]]
      
      # sort排序,返回排序后的新数组
      b1 = np.sort(a)
      print(b1)
      # [[10 11 15 22 35]
      #  [ 6 13 16 22 41]
      #  [ 5 19 21 32 85]
      #  [12 21 26 33 56]]
      
      # argsorg,返回排序后元素在原数组中的索引位置
      b1 = np.argsort(a)
      print(b1)
      # [[2 0 1 3 4]
      #  [3 2 4 1 0]
      #  [1 2 0 3 4]
      #  [1 0 3 2 4]]
      
      # sort排序,返回排序后的新数组
      b1 = np.sort(a, axis=0)
      print(b1)
      # [[11  5 10  6 16]
      #  [21 12 13 22 35]
      #  [21 15 19 26 56]
      #  [41 22 33 32 85]]
      
      # argsorg,返回排序后元素在原数组中的索引位置
      b1 = np.argsort(a, axis=0)
      print(b1)
      # [[0 2 0 1 1]
      #  [2 3 1 0 0]
      #  [3 0 2 3 3]
      #  [1 1 3 2 2]]
      
      # sort排序,返回排序后的新数组
      b1 = np.sort(a, axis=1)
      print(b1)
      # [[10 11 15 22 35]
      #  [ 6 13 16 22 41]
      #  [ 5 19 21 32 85]
      #  [12 21 26 33 56]]
      
      # argsorg,返回排序后元素在原数组中的索引位置
      b1 = np.argsort(a, axis=1)
      print(b1)
      # [[2 0 1 3 4]
      #  [3 2 4 1 0]
      #  [1 2 0 3 4]
      #  [1 0 3 2 4]]
      
  • 获取满足条件的元素的索引:argwhere
    • 返回数组内符合条件的元素的索引值
    • 语法
      numpy.argwhere(a)
      
      # 参数详解
          # a:条件表达式
      
      # 条件表达式也可以使用 & 且 和 | 或
      numpy.argwhere((a1) & (a2))
      numpy.argwhere((a1) | (a2))
      
    • 示例
      import numpy as np
      
      a = np.arange(20).reshape(4, 5)
      print(a)
      # [[ 0  1  2  3  4]
      #  [ 5  6  7  8  9]
      #  [10 11 12 13 14]
      #  [15 16 17 18 19]]
      
      # 数组布尔数组索引切片,返回的是满足条件的元素
      b1 = a[a>5]
      print(b1)
      # [ 6  7  8  9 10 11 12 13 14 15 16 17 18 19]
      
      # numpy.argwhere返回的是满足条件元素的索引
      b2 = np.argwhere(a>5)
      print(b2)
      # [[1 1]
      #  [1 2]
      #  [1 3]
      #  [1 4]
      #  [2 0]
      #  [2 1]
      #  [2 2]
      #  [2 3]
      #  [2 4]
      #  [3 0]
      #  [3 1]
      #  [3 2]
      #  [3 3]
      #  [3 4]]
      
      # 数组布尔数组索引切片,返回的是满足条件的元素
      c1 = a[(a > 5) & (a < 10)]
      print(c1)
      # [6 7 8 9]
      
      # numpy.argwhere返回的是满足条件元素的索引
      c2 = np.argwhere((a>5) & (a<10))
      print(c2)
      # [[1 1]
      #  [1 2]
      #  [1 3]
      #  [1 4]]
      
  • 获取最大值和最小值的索引:argmax、argmin
  • 语法
    argmax(a, axis=None, out=None, *, keepdims=np._NoValue)
    
    argmin(a, axis=None, out=None, *, keepdims=np._NoValue)
    
  • 示例
    import numpy as np
    
    a = np.array([[11, 15, 10, 22, 35],[41, 22, 13, 6, 16],[21, 5, 19, 32, 85],[21, 12, 33, 26, 56]])
    print(a)
    # [[11 15 10 22 35]
    #  [41 22 13  6 16]
    #  [21  5 19 32 85]
    #  [21 12 33 26 56]]
    
    b1 = np.argmax(a)
    print(b1)    # ---> 14
    
    c1 = np.argmin(a)
    print(c1)    # ---> 11
    
    b2 = np.argmax(a, axis=0)
    print(b2)
    # [1 1 3 2 2]
    
    c2 = np.argmin(a, axis=0)
    print(c2)
    # [0 2 0 1 1]
    
    b3 = np.argmax(a, axis=1)
    print(b3)
    # [4 0 4 4]
    
    c3 = np.argmin(a, axis=1)
    print(c3)
    # [2 3 1 1]
    
Numpy文件操作
常用方法
  • 读取文件
    loadtxt()
    genfromtxt()
    
  • 保存文件
    savetxt()
    

loadtxt()
  • 语法
    loadtxt(fname, dtype=float, comments='#', delimiter=None, converters=None, skiprows=0, usecols=None, unpack=False, ndmin=0, encoding='bytes', max_rows=None, *, quotechar=None, like=None)
    
    # 参数说明
        # fname
            # 字符串类型,目标文件地址,支持压缩文件(包括gz、bz格式)
        # dtype
            # 指定存储读取到的数据的数据类型,默认float
        # comments
            # 字符串或字符串组成的列表类型,注释字符集开始的标志,默认为 #
        # delimiter
            # 字符串类型,数据中使用的分隔符
        # converters
            # 字典类型,将特定列的数据转换为字典中对应的函数的浮点型数据,默认为空(例如:将空值转换为0)
            # converters={列索引: 处理值的函数}
        # skiprows
            # 跳过第一skiprows行,包括注释;默认值:0(例如跳过第一行标题或注释)
        # usecols
            # 元组类型,用来指定要读取数据的列,默认为空(第一列为0)
        # unpack
            # 布尔类型,指定是否专职数组,默认为False
        # ndmin
            # 整数类型,指定返回的数组至少包含特定维度的数组,默认为0
        # encoding
            # 指定编码类型
        # max_rows
            # 指定读取的总行数为max_rows。默认值是读取所有行
        # quotechar   
        # like    
    
    # 返回值
        从文件中读取的数组
    
loadtxt()的应用场景
    • 读取CSV文件
      • CSV(逗号分隔值)文件是一种常见的文本文件格式,用于存储表格数据。
      • 使用numpy.loadtxt()可以方便地读取CSV文件,并将其转换为NumPy数组。
      • 通过指定delimiter=‘,’,可以告诉函数使用逗号作为分隔符。
    • 读取空格分隔的文件
      • 除了CSV文件外,还有很多文本文件使用空格、制表符或其他空白字符作为分隔符。
      • 对于这类文件,numpy.loadtxt()同样适用。默认情况下,它会将任何空白字符作为分隔符来解析数据。
    • 跳过不需要的行
      • 如果文本文件中包含标题行、注释行或其他不需要的数据行,可以使用skiprows参数来跳过它们。
    • 选择特定的列
      • 在处理多列文本文件时,有时我们只对其中的某些列感兴趣。通过usecols参数,指定要读取的列
loadtxt()的注意事项
    • 文件编码
      • 确保文件的编码与Python环境的编码一致,否则在读取文件时可能会出现编码错误。
      • 如果文件使用非默认编码(如UTF-8),需要在打开文件时指定正确的编码。
    • 数据类型匹配
      • 在读取数据时,要确保指定的数据类型与文件中的实际数据类型相匹配。
      • 如果数据类型不匹配,可能会导致读取错误或数据解析异常。
    • 异常处理
      • 在读取文件时,可能会遇到各种异常情况,如文件不存在、文件格式错误等。
      • 为了增强代码的健壮性,应该添加适当的异常处理机制,如使用try-except块来捕获并处理潜在的异常。
    • 内存管理
      • 当处理大型文本文件时,读取的数据可能会占用大量内存。
      • 确保系统有足够的内存来存储整个数据集,或者考虑使用分块读取的方式,避免一次性加载整个文件到内存中
loadtxt()与genfromtxt()的比较
  • 对于简单的文本文件,numpy.loadtxt()可能是一个足够好的选择
  • 对于更复杂的文本文件,可能需要考虑使用numpy.genfromtxt()或其他更高级的工具

genfromtxt()
  • 是numpy.loadtxt()的一个更通用的版本
  • 提供了更多的选项和灵活性,可以处理更复杂的文本文件
  • 例如,它可以处理缺失值、不同行具有不同列数的情况等
  • genfromtxt()主要执行两个循环运算
    • 第一个循环将文件的每一行转换成字符串序列
    • 第二个循环将每个字符串序列转换为相应的数据类型
  • 语法
    genfromtxt(fname, dtype=float, comments='#', delimiter=None, skip_header=0, skip_footer=0, converters=None, missing_values=None, filling_values=None, usecols=None, names=None, excludelist=None, deletechars=''.join(sorted(NameValidator.defaultdeletechars)), replace_space='_', autostrip=False, case_sensitive=True, defaultfmt="f%i", unpack=None, usemask=False, loose=True, invalid_raise=True, max_rows=None, encoding='bytes', *, ndmin=0, like=None)
    
    # 参数详解
    # dtype
        # 从文件读取的字符串序列要转换为其他类型数据时需设置dtype参数。默认是float类型
        # 单个类型,如dtype =float。
        # 一个序列类型,例如dtype=(int, float, float).
        # 一个逗号分隔的字符串,例如dtype="i4,f8,|S3".
        # 一个字典包含两个键‘names’和‘formats’
        # 一个元组序列,例如dtype = [('A',int),('B',float)]
        # 一个存在的numpy.dtype对象
        # 一个特殊的值None,在这种情况下,每个列的类型有自身数据决定。
        # 将参数设置成None效率较低。因为它会从布尔值开始检验,然后是整型,浮点型,复数最后是字符串,直到满足条件为止
    # comments
        # 字符串类型,标志着一个注释的开始符号。默认是"#"
        # 在转换过程中注释标记可能发生在任何地方。任何字符出现在在注释标记之后会被忽略
        # 注意:这种行为有一个例外:如果可选的参数names=True,第一行检查到注释行会被认为是名称
    # delimiter
        # 
    # skip_header和skip_footer
        # 一个文件的页眉会阻碍文件的处理。在这种情况下,我们需要使用skip_header可选参数。
        # 这个参数的值必须是一个整数,跳过文件开头的对应的行数,然后再执行任何其他操作。
        # 同样的,我们通过使用skip_footer属性和n的值可以跳过文件的最后n行。默认值都为0
    # converters
        # 当我们希望日期的格式MM/DD/YYYY被转换为一个datetime对象,或一个字符串xx%正确地转换为一个浮点数在0和1之间时,需要使用converters参数定义转换函数。
        # 这个参数的值通常是一个以列索引或列名称作为键和一个转换函数作为值的字典。
        # 这些转换函数可以是实际的函数或lambda函数。
        # 在任何情况下,他们应该只接受一个字符串作为输入和输出和只有一个想要得到的元素类型
    # missing_values
        # 默认情况下使用空格表示缺失,我们可以使用更复杂的字符表示缺失
        # 例如'N/A'或'???'。missing_values接受三种类型的值:
        # 一个字符串或逗号分隔的字符串:这个字符串将被用作标记的缺失数据的所有列
        # 一个字符串序列:在这种情况下,按照顺序每一项与对应的列相关联。
        # 一个字典:字典的值是字符串或字符串序列。对应的key可以列索引(整数)或列名(字符串)
        # 此外,key=none定义一个默认值的适用于所有列
    # filling_values
        # 出现缺失值时,系统默认填充的值:
            # Expected type    # Default
            # bool             # False
            # int              # -1
            # float            # np.nan
            # complex          # np.nan+0j
            # string           # '???'
        
        # 我们也可以像missing_values参数自定义设置参数的值。
        # filling_values接受三种类型的值:
            # 一个单独的值:所有列的默认值
            # 一个序列的值:按照顺序每一项对应相应列。
            # 一个字典:字典的值是一个单独的对象。对应的key可以列索引(整数)或列名(字符串)。此外,key=none定义一个默认值的适用于所有列
    # usercols
        # 使用usecols指定需要读取的列
        # 这个参数接受一个整数或一个整数序列作为索引
        # 第一列的索引0,-1对应最后一列。
        # 如果列有名称,我们也可以将usecols参数设置为他们的名称,或者包含列名称的字符串序列或逗号分隔的字符串
    # names
        # 可以将names参数设置为true并跳过第一行,程序将把第一行作为列名称,即使第一行被注释掉了也会被读取。
        # 或可以使用dtype设置名称,也可以重写names,默认的names是none
        # 当names=none时,将有numpy产生一些标准默认的值"f%i",我们可以通过defaultfmt改变默认格式
    # 验证names:三个可选参数,提供了一个更好的控制上的名字
        # excludelist
            # 给出一系列要删除的name,如return,file,print……如果其中一个输入的名字出现在这个列表中,将会给它附加一个下划线(“_”)
        # deletechars
            # 一个name中所有包含的需要删除的连接符。默认情况下无效字符~!@#$%^&*()——+~=\|]}({;:/?>,<
        # case_sensitive
            # 名字是否应该区分大小写(case_sensitive = True)
            # 转换为大写(case_sensitive=False or case_sensitive='upper')
            # 转换为小写(case_sensitive='lower')
    # replace_space
        # 
    # autostrip
        # 自动去除空格,默认是False
        # 当把一行分割成一个字符串序列,序列中的每一项前后的多余空格还存在
    # defaultfmt
        # 默认是"f%i"
    # unpack
        # 
    # usemask
        # 我们可能还想跟踪缺失数据的发生通过构造一个Boolean mask,数据缺失的地方返回true,否则,则返回False。
        # 要做到这一点,我们必须设置可选参数usemask=True(默认是False)。结果将输出一个MaskedArray数组
    # loose
        # 
    # invalid_raise
        # 
    # max_rows
        # 
    # encoding
        # 
    # ndmin=0
        # 
    # like
        # 
    

savetxt()
  • 与numpy.loadtxt()相反,用于数据的输出和保存,将NumPy数组保存为文本文件
  • 语法
    savetxt(fname, X, fmt='%.18e', delimiter=' ', newline='\n', header='', footer='', comments='# ', encoding=None)
    
    # 参数详解
        # fname       # 字符串,文件名,或者文件对象
                      # 如果参数中没有扩展名,默认保存为.txt文件
                      # 如果文件名以“.gz”结尾,文件将自动保存为gzip压缩格式
        # X           # 数组,要保存的数据。它可以是一维或二维的
        # fmt         # 字符串,写入文件的格式,默认为 %.18e
                      # 单一格式:fmt='%s'
                      # 多种格式:fmt='%.2f %.3f %.4f, %e, %.5f'
                      # 格式列表:fmt=['%d', '%.2f', '%d', '%.3f', '%d']
                      # %s:字符串,%d:数字型,%f:小数型,%e: 科学计数
        # delimiter   # 字符串,分隔符,默认为 空格
        # newline     # 字符串,换行符,默认为 \n
        # header      # 字符串,文件头部添加的内容,默认为空
        # footer      # 字符串,文件尾部添加的内容,默认为空
        # comments    # 字符串,附加到header和footer内容前的字符串,标记其为注释,默认以 # 开头
        # encoding    # 字符串,编码方式,默认为 None
    


loadtxt()示例
  • 默认参数读取文件
    • 文件信息:data.txt
      0 1 2 3 4 5 6 7 8 9
      10 11 12 13 14 15 16 17 18 19
      20 21 22 23 24 25 26 27 28 29
      30 31 32 33 34 35 36 37 38 39
      40 41 42 43 44 45 46 47 48 49
      50 51 52 53 54 55 56 57 58 59
      60 61 62 63 64 65 66 67 68 69
      70 71 72 73 74 75 76 77 78 79
      80 81 82 83 84 85 86 87 88 89
      90 91 92 93 94 95 96 97 98 99
      
    • 读取文件内容
      import numpy as np
      
      result = np.loadtxt('data.txt')
      print(result)
      
      # 输出结果
      [[ 0.  1.  2.  3.  4.  5.  6.  7.  8.  9.]
      [10. 11. 12. 13. 14. 15. 16. 17. 18. 19.]
      [20. 21. 22. 23. 24. 25. 26. 27. 28. 29.]
      [30. 31. 32. 33. 34. 35. 36. 37. 38. 39.]
      [40. 41. 42. 43. 44. 45. 46. 47. 48. 49.]
      [50. 51. 52. 53. 54. 55. 56. 57. 58. 59.]
      [60. 61. 62. 63. 64. 65. 66. 67. 68. 69.]
      [70. 71. 72. 73. 74. 75. 76. 77. 78. 79.]
      [80. 81. 82. 83. 84. 85. 86. 87. 88. 89.]
      [90. 91. 92. 93. 94. 95. 96. 97. 98. 99.]]
      
      • 默认读取后的数据存储为float类型
  • dtype参数:指定存储类型
    import numpy as np
    
    result = np.loadtxt('data.txt', dtype='i1')
    print(result)
    
    # 输出结果
    [[ 0  1  2  3  4  5  6  7  8  9]
     [10 11 12 13 14 15 16 17 18 19]
     [20 21 22 23 24 25 26 27 28 29]
     [30 31 32 33 34 35 36 37 38 39]
     [40 41 42 43 44 45 46 47 48 49]
     [50 51 52 53 54 55 56 57 58 59]
     [60 61 62 63 64 65 66 67 68 69]
     [70 71 72 73 74 75 76 77 78 79]
     [80 81 82 83 84 85 86 87 88 89]
     [90 91 92 93 94 95 96 97 98 99]]
    
  • comments参数:指定注释标志
    • 文件信息:data1.txt
      -- 0 0 0 0 0 0 0 0 0
      0 1 2 3 4 5 6 7 8 9
      10 11 12 13 14 15 16 17 18 19
      20 21 22 23 24 25 26 27 28 29
      30 31 32 33 34 35 36 37 38 39
      40 41 42 43 44 45 46 47 48 49
      50 51 52 53 54 55 56 57 58 59
      60 61 62 63 64 65 66 67 68 69
      70 71 72 73 74 75 76 77 78 79
      80 81 82 83 84 85 86 87 88 89
      90 91 92 93 94 95 96 97 98 99
      
    • 读取文件
      import numpy as np
      
      result = np.loadtxt('data1.txt', dtype=object)
      print(result)
      # [['--' '0' '0' '0' '0' '0' '0' '0' '0' '0']
      #  ['0' '1' '2' '3' '4' '5' '6' '7' '8' '9']
      #  ['10' '11' '12' '13' '14' '15' '16' '17' '18' '19']
      #  ['20' '21' '22' '23' '24' '25' '26' '27' '28' '29']
      #  ['30' '31' '32' '33' '34' '35' '36' '37' '38' '39']
      #  ['40' '41' '42' '43' '44' '45' '46' '47' '48' '49']
      #  ['50' '51' '52' '53' '54' '55' '56' '57' '58' '59']
      #  ['60' '61' '62' '63' '64' '65' '66' '67' '68' '69']
      #  ['70' '71' '72' '73' '74' '75' '76' '77' '78' '79']
      #  ['80' '81' '82' '83' '84' '85' '86' '87' '88' '89']
      #  ['90' '91' '92' '93' '94' '95' '96' '97' '98' '99']]
      
      result1 = np.loadtxt('data1.txt', dtype=object, comments='--')
      print(result1)
      # [['0' '1' '2' '3' '4' '5' '6' '7' '8' '9']
      #  ['10' '11' '12' '13' '14' '15' '16' '17' '18' '19']
      #  ['20' '21' '22' '23' '24' '25' '26' '27' '28' '29']
      #  ['30' '31' '32' '33' '34' '35' '36' '37' '38' '39']
      #  ['40' '41' '42' '43' '44' '45' '46' '47' '48' '49']
      #  ['50' '51' '52' '53' '54' '55' '56' '57' '58' '59']
      #  ['60' '61' '62' '63' '64' '65' '66' '67' '68' '69']
      #  ['70' '71' '72' '73' '74' '75' '76' '77' '78' '79']
      #  ['80' '81' '82' '83' '84' '85' '86' '87' '88' '89']
      #  ['90' '91' '92' '93' '94' '95' '96' '97' '98' '99']]
      
      # 没有指定comments参数时,第一行的注释内容也读取到了
      # 指定了comments之后,第一行注释内容直接被过滤掉了
      
  • delimiter参数:指定数据中的分隔符
    • 文件信息:data2.txt
      0,1,2,3,4,5,6,7,8,9
      10,11,12,13,14,15,16,17,18,19
      20,21,22,23,24,25,26,27,28,29
      30,31,32,33,34,35,36,37,38,39
      40,41,42,43,44,45,46,47,48,49
      
    • 读取文件
      import numpy as np
      
      result = np.loadtxt('data2.txt', dtype=object)
      print(result)
      # ['0,1,2,3,4,5,6,7,8,9' '10,11,12,13,14,15,16,17,18,19'
      #  '20,21,22,23,24,25,26,27,28,29' '30,31,32,33,34,35,36,37,38,39'
      #  '40,41,42,43,44,45,46,47,48,49']
      
      result1 = np.loadtxt('data2.txt', dtype=object,delimiter=',')
      print(result1)
      # [['0' '1' '2' '3' '4' '5' '6' '7' '8' '9']
      #  ['10' '11' '12' '13' '14' '15' '16' '17' '18' '19']
      #  ['20' '21' '22' '23' '24' '25' '26' '27' '28' '29']
      #  ['30' '31' '32' '33' '34' '35' '36' '37' '38' '39']
      #  ['40' '41' '42' '43' '44' '45' '46' '47' '48' '49']]
      
      # 未指定文件内容分隔符时,系统默认分隔符为空格,将文件中一行数据默认为一个元素
      # 制定分隔符之后,会按照分隔符将数据分成单独元素
      
  • converters参数:特定列的数据转换为字典中对应的函数的浮点型数据
    • 文件信息
      0,1,2,3,4,5,6,7,8,9
      10,11,12,13,14,15,16,17,18,19
      20,21,22,23,,25,26,27,28,29
      30,31,32,33,34,35,36,37,38,39
      40,41,42,43,44,,46,47,48,49
      
      # 注意:文件数据中,第三行第五列和第五行第六列没有数据
      
    • 读取文件
      import numpy as np
      
      # result = np.loadtxt('data3.txt', delimiter=',')
      # print(result)
      # 报错:could not convert string '' to float64 at row 2, column 5.
      
      
      def test(num):
          try:
              return float(num)
          except:
              return 0
      
      # 在使用converters参数时,需要通过列索引指定对哪一列的数据进行容错处理
      # 会把指定列的元素,一个一个通过函数进行处理,获取到返回值再写入到数组中
      result1 = np.loadtxt('data3.txt', delimiter=',', converters={4: test, 5: test})
      print(result1)
      # [[ 0.  1.  2.  3.  4.  5.  6.  7.  8.  9.]
      #  [10. 11. 12. 13. 14. 15. 16. 17. 18. 19.]
      #  [20. 21. 22. 23.  0. 25. 26. 27. 28. 29.]
      #  [30. 31. 32. 33. 34. 35. 36. 37. 38. 39.]
      #  [40. 41. 42. 43. 44.  0. 46. 47. 48. 49.]]
      
  • skiprows参数:跳过前几行,包括注释
    • 数据信息:student.txt
      name1 gender age height
      name2 gender age height
      zhangs nan 18 170
      lis nv 19 165
      wangw nv 18 160
      zhaol nan 18 190
      
    • 读取文件
      import numpy as np
      
      result = np.loadtxt('student.txt', dtype=object)
      print(result)
      # [['name1' 'gender' 'age' 'height']
      #  ['name2' 'gender' 'age' 'height']
      #  ['zhangs' 'nan' '18' '170']
      #  ['lis' 'nv' '19' '165']
      #  ['wangw' 'nv' '18' '160']
      #  ['zhaol' 'nan' '18' '190']]
      
      result1 = np.loadtxt('student.txt', dtype=object, skiprows=2)
      print(result1)
      # [['zhangs' 'nan' '18' '170']
      #  ['lis' 'nv' '19' '165']
      #  ['wangw' 'nv' '18' '160']
       # ['zhaol' 'nan' '18' '190']]
       
       # 没有指定skiprows参数时,文件中的表头行也读取到了数组中
      
  • usecols参数:指定要读取数据的列
    • 文件信息:student1.txt
      name gender age height
      zhangs nan 18 170
      lis nv 19 165
      wangw nv 18 160
      zhaol nan 18 190
      
    • 读取文件
      import numpy as np
      
      result = np.loadtxt('student1.txt', dtype=object, skiprows=1)
      print(result)
      # [['zhangs' 'nan' '18' '170']
      #  ['lis' 'nv' '19' '165']
      #  ['wangw' 'nv' '18' '160']
      #  ['zhaol' 'nan' '18' '190']]
      
      
      result1 = np.loadtxt('student1.txt', dtype=int, skiprows=1,usecols=2)
      print(result1)
      # [18 19 18 18]
      
      print(np.mean(result1))     # --> 18.25
      
      # 要计算文件中所有人员的平均年龄
      # 如果我们读取所有数据,不仅占用内存,而且获取到的数据类型是文本,不方便计算
      # 使用usecols指定读取列,并指定数据存储类型为int,那么就可以直接进行平均值的计算了
      
  • unpack参数:指定是否转置数组
    • 文件信息:data2.txt
      0,1,2,3,4,5,6,7,8,9
      10,11,12,13,14,15,16,17,18,19
      20,21,22,23,24,25,26,27,28,29
      30,31,32,33,34,35,36,37,38,39
      40,41,42,43,44,45,46,47,48,49
      
    • 读取数据
      import numpy as np
      
      result = np.loadtxt('data2.txt',delimiter=',')
      print(result)
      # [[ 0.  1.  2.  3.  4.  5.  6.  7.  8.  9.]
      #  [10. 11. 12. 13. 14. 15. 16. 17. 18. 19.]
      #  [20. 21. 22. 23. 24. 25. 26. 27. 28. 29.]
      #  [30. 31. 32. 33. 34. 35. 36. 37. 38. 39.]
      #  [40. 41. 42. 43. 44. 45. 46. 47. 48. 49.]]
      
      result1 = np.loadtxt('data2.txt',delimiter=',',unpack=True)
      print(result1)
      # [[ 0. 10. 20. 30. 40.]
      #  [ 1. 11. 21. 31. 41.]
      #  [ 2. 12. 22. 32. 42.]
      #  [ 3. 13. 23. 33. 43.]
      #  [ 4. 14. 24. 34. 44.]
      #  [ 5. 15. 25. 35. 45.]
      #  [ 6. 16. 26. 36. 46.]
      #  [ 7. 17. 27. 37. 47.]
      #  [ 8. 18. 28. 38. 48.]
      #  [ 9. 19. 29. 39. 49.]]
      
  • ndmin参数:指定返回的数组至少包含z维度的数组
    • 文件信息:student1.txt
      name gender age height
      zhangs nan 18 170
      lis nv 19 165
      wangw nv 18 160
      zhaol nan 18 190
      
    • 读取数据
      import numpy as np
      
      result = np.loadtxt('student1.txt', dtype=int, skiprows=1,usecols=2)
      print(result)
      # [18 19 18 18]
      
      result1 = np.loadtxt('student1.txt', dtype=int, skiprows=1,usecols=2, ndmin=2)
      print(result1)
      # [[18]
      #  [19]
      #  [18]
      #  [18]]
      
  • encoding参数:指定编码类型
  • 文件信息:student.csv
    姓名,性别,年龄,身高
    张三,男,18,170
    李四,女,19,165
    王五,女,18,160
    赵六,男,18,190
    
  • 读取文件
    import numpy as np
    
    # result = np.loadtxt('student.csv', dtype=object)
    # print(result)
    # 报错
    # UnicodeDecodeError: 'gbk' codec can't decode byte 0xab in position 23: illegal multibyte sequence
    
    result1 = np.loadtxt('student.csv', dtype=object,delimiter=',', encoding='utf-8')
    print(result1)
    # [['姓名' '性别' '年龄' '身高']
    #  ['张三' '男' '18' '170']
    #  ['李四' '女' '19' '165']
    #  ['王五' '女' '18' '160']
    #  ['赵六' '男' '18' '190']]
    
    # 文件内容包含了中文,直接读取会报错:'gbk'编解码器无法解码
    # 需要通过encoding指定编码类型为'utf-8',再进行读取
    
  • max_rows参数:指定读取的总行数
    • 文件信息:student.csv
      姓名,性别,年龄,身高
      张三,男,18,170
      李四,女,19,165
      王五,女,18,160
      赵六,男,18,190
      舟山,男,20,177
      王灿,女,21,168
      田彩,女,20,171
      
    • 读取文件
      import numpy as np
      
      result = np.loadtxt('student.csv', dtype=object,delimiter=',', encoding='utf-8')
      # print(result)
      # [['姓名' '性别' '年龄' '身高']
      #  ['张三' '男' '18' '170']
      #  ['李四' '女' '19' '165']
      #  ['王五' '女' '18' '160']
      #  ['赵六' '男' '18' '190']
      #  ['舟山' '男' '20' '177']
      #  ['王灿' '女' '21' '168']
      #  ['田彩' '女' '20' '171']]
      
      result1 = np.loadtxt('student.csv', dtype=object,delimiter=',', encoding='utf-8', max_rows=2)
      print(result1)
      [['姓名' '性别' '年龄' '身高']
       ['张三' '男' '18' '170']]
      
      result2 = np.loadtxt('student.csv', dtype=object, delimiter=',', encoding='utf-8', skiprows=1, max_rows=2)
      print(result2)
      # [['张三' '男' '18' '170']
      #  ['李四' '女' '19' '165']]
      
      # 不指定max_row参数时,默认读取到最后一行
      # 指定max_row参数后,从开始行(skiprows)开始,读取max_row行数据
      
  • 读取文件存储为结构化数据类型
    • 文件信息:student.csv
      姓名,性别,年龄,身高
      张三,男,18,170
      李四,女,19,165
      王五,女,18,160
      赵六,男,18,190
      舟山,男,20,177
      王灿,女,21,168
      田彩,女,20,171
      
    • 文件操作
      import numpy as np
      
      # 定义结构化数据类型
      dt = np.dtype([('name', 'U4'), ('gender', 'U1'), ('age', 'i1'), ('height', 'i4')])
      
      # 读取文件
      student = np.loadtxt('student.csv', dtype=dt, skiprows=1, encoding='utf-8', delimiter=',')
      print(student)
      
      # [('张三', '男', 18, 170) ('李四', '女', 19, 165) ('王五', '女', 18, 160)
      #  ('赵六', '男', 18, 190) ('舟山', '男', 20, 177) ('王灿', '女', 21, 168)
      #  ('田彩', '女', 20, 171)]
      
      # 根据需求取值
      print('age:', student['age'])
      # age: [18 19 18 18 20 21 20]
      
      print('nane:', student['name'])
      # nane: ['张三' '李四' '王五' '赵六' '舟山' '王灿' '田彩']
      

genfromtxt()示例
savetxt()示例
  • fmt参数:写入文件的格式
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a.txt', arr_a, fmt='%.1f')
    # arr_a.txt
    # 0.0  1.0  2.0  3.0  4.0
    # 5.0  6.0  7.0  8.0  9.0
    # 10.0 11.0 12.0 13.0 14.0
    # 15.0 16.0 17.0 18.0 19.0
    
    np.savetxt('arr_a1.txt', arr_a, fmt='%d %.1f %s %d %e')
    # arr_a1.txt
    # 0  1.0  2  3  4.000000e+00
    # 5  6.0  7  8  9.000000e+00
    # 10 11.0 12 13 1.400000e+01
    # 15 16.0 17 18 1.900000e+01
    
    np.savetxt('arr_a2.txt', arr_a, fmt=['%d', '%.2f', '%d', '%.3f', '%d'])
    # arr_a2.txt
    # 0  1.00  2  3.000  4
    # 5  6.00  7  8.000  9
    # 10 11.00 12 13.000 14
    # 15 16.00 17 18.000 19
    
  • delimiter参数:分隔符
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a3.txt', arr_a, fmt='%d',delimiter=',')
    # arr_a3.txt
    # 0,1,2,3,4
    # 5,6,7,8,9
    # 10,11,12,13,14
    # 15,16,17,18,19
    
  • newline参数:换行符
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a4.txt', arr_a, fmt='%d',newline=',')
    # arr_a4.txt
    # 0 1 2 3 4,5 6 7 8 9,10 11 12 13 14,15 16 17 18 19,
    
  • header参数:文件头部添加的内容
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a5.txt', arr_a, fmt='%d', header='savetxt保存文件')
    # arr_a5.txt
    # # savetxt�����ļ�
    # 0 1 2 3 4
    # 5 6 7 8 9
    # 10 11 12 13 14
    # 15 16 17 18 19
    
    # 由于没有指定编码格式为utf-8,导致中文保存成乱码
    
  • footer参数:文件尾部添加的内容
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a6.txt', arr_a, fmt='%d', footer='savetxtfile')
    # arr_a6.txt
    # 0 1 2 3 4
    # 5 6 7 8 9
    # 10 11 12 13 14
    # 15 16 17 18 19
    # # savetxtfile
    
  • comments参数:附加到header和footer内容前的字符串,标记其为注释
    import numpy as np
    
    arr_a = np.arange(20).reshape(4, 5)
    print(arr_a)
    # [[ 0  1  2  3  4]
    #  [ 5  6  7  8  9]
    #  [10 11 12 13 14]
    #  [15 16 17 18 19]]
    
    np.savetxt('arr_a8.txt', arr_a, fmt='%s',header='This is the header',footer='This is the footer', comments='-- ')
    # arr_a8.txt
    # -- This is the header
    # 0 1 2 3 4
    # 5 6 7 8 9
    # 10 11 12 13 14
    # 15 16 17 18 19
    # -- This is the footer
    
  • encoding参数:编码方式
    import numpy as np
    
    arr_a = np.array([['姓名','性别','年龄'],['张三','男',22],['李四','女',23],['王五','男',31]])
    print(arr_a)
    # [['姓名' '性别' '年龄']
    #  ['张三' '男' '22']
    #  ['李四' '女' '23']
    #  ['王五' '男' '31']]
    
    np.savetxt('arr_a9.txt',arr_a,fmt='%s')
    # arr_a9.txt
    # ���� �Ա� ����
    # ���� �� 22
    # ���� ٠23
    # ���� �� 31
    
    np.savetxt('arr_a10.txt',arr_a,fmt='%s',encoding='utf-8')
    # arr_a10.txt
    # 姓名 性别 年龄
    # 张三 男 22
    # 李四 女 23
    # 王五 男 31
    
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
numpy是一个开源的Python科学计算库,它提供了一个强大的多维数组对象和用于处理这些数组的函数。下面是关于numpy模块的详细解释: 1. 数组:numpy最重要的特性之一是它的数组对象(numpy.ndarray)。这是一个由相同类型的元素组成的多维容器。数组可以是一维、二维、三维等等,并且可以包含整数、浮点数、复数等不同类型的数据。 2. 数组操作:numpy提供了一系列用于操作数组的函数和方法。你可以进行基本的数学运算(加、减、乘、除等)、统计计算(平均值、标准差等)、逻辑运算(与、或、非等)以及数组的切片、索引等操作。 3. 广播:numpy的广播功能使得不同形状的数组之间的运算成为可能。它可以自动调整不同形状数组的大小,使得它们能够进行元素级别的运算。 4. 矩阵操作:numpy还提供了许多矩阵操作的函数和方法。你可以进行矩阵的转置、求逆、乘法、求特征值和特征向量等操作。 5. 随机数生成:numpy包含了一个random子模块,用于生成各种类型的随机数。你可以生成服从特定分布(如正态分布、均匀分布等)的随机数,并进行各种随机抽样操作。 6. 文件操作:numpy可以读取和写入数组数据到磁盘。它支持多种数据格式,包括文本文件、二进制文件和压缩文件。 总之,numpy提供了丰富的功能和高效的数组操作,使得Python成为一种强大的科学计算语言。它在数据分析、机器学习、图像处理等领域广泛应用。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

失心疯_2023

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

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

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

打赏作者

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

抵扣说明:

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

余额充值