zoukankan      html  css  js  c++  java
  • Numpy库

    NumPy之于数值计算特别重要的原因之一,是因为它可以高效处理大数组的数据。这是因为:

    • NumPy是在一个连续的内存块中存储数据,独立于其他Python内置对象。NumPy的C语言编写的算法库可以操作内存,而不必进行类型检查或其它前期工作。比起Python的内置序列,NumPy数组使用的内存更少。
    • NumPy可以在整个数组上执行复杂的计算,而不需要Python的for循环。

    一、创建ndarray

    (1)arange()函数:

    调用格式:arange(start,stop,step)
    start:间隔开始。间隔包括此值,默认开始值为0。
    stop:间隔结束。间隔不包括此值。
    step:间隔步长。
    例子:
    import numpy as np
    >>> np.arange(3)
    #array([0, 1, 2])
    >>> np.arange(3.0)
    #array([ 0.,  1.,  2.])
    >>> np.arange(3,7)
    #array([3, 4, 5, 6])
    >>> np.arange(3,7,2)
    #array([3, 5])

       arr = np.arange(32).reshape((8, 4))

    (2)random模块:随机数生成

             rand():函数根据给定维度生成[0,1)之间的数据,包含0,不包含1。如:>>> data1 = np.random.rand(2,3)

             randn():函数根据给定维度生成一个或一组样本,具有标准正态分布。如:>>>data2 =  np.random.randn(2,3)

      (3)  每个数组都有一个shape(一个表示各维度大小的元组)和一个dtype(一个用于说明数组数据类型的对象)属性。         

    >>> data.shape
    #(2,3)
    >>> data.dtype
    #float64
    >>> data.ndim
    #2

    (4)创建数组函数

             array函数:它接受一切序列型的对象(包括其他数组),然后产生一个新的含有传入数据的NumPy数组。

    >>> data1 = [1,2,3,4]
    >>> data2 = [[1,3,4,6],[2,4,6,9]]
    >>> data_arr1 = np.array(data1)
    >>> data_arr2 = np.array(data2)
    >>> print(data_arr1)
    >>> print(data_arr2)
    [1 2 3 4]

    [[1 3 4 6]
    [2 4 6 9]]

           除np.array之外,还有一些函数也可以新建数组。比如,zeros和ones分别可以创建指定长度或形状的全0或全1数组。empty可以创建一个没有任何具体值的数组。要用这些方法创建多维数组,只需传入一个表示形状的元组。

    二、ndarray的数据类型

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

      arr1 = np.array([1, 2, 3], dtype=np.float64)

          可以通过ndarray的astype方法明确地将一个数组从一个dtype转换成另一个dtype:

    >>> arr = np.array([1, 2, 3, 4, 5])
    >>> arr.dtype

    dtype('int64')

    >>> float_arr = arr.astype(np.float64)
    >>> float_arr.dtype

    dtype('float64')

    调用astype总会创建一个新的数组(一个数据的备份),即使新的dtype与旧的dtype相同。

    三、numpy数组的运算

            数组很重要,因为它使你不用编写循环即可对数据执行批量运算。NumPy用户称其为矢量化(vectorization)。大小相等的数组之间的任何算术运算都会将运算应用到元素级。

    arr = np.array([[2,4,6,8],[1,4,7,3]])
    print(arr)
    print(arr*arr)
    print(arr-arr)

    [[2 4 6 8]
    [1 4 7 3]]


    [[ 4 16 36 64]
    [ 1 16 49 9]]


    [[0 0 0 0]
    [0 0 0 0]]

            数组与标量的算术运算会将标量值传播到各个元素:

    print(1/arr)
    print(arr**0.5) 

    [[0.5 0.25 0.16666667 0.125 ]
    [1. 0.25 0.14285714 0.33333333]]

    [[1.41421356 2. 2.44948974 2.82842712]
    [1. 2. 2.64575131 1.73205081]]

         大小相同的数组之间的比较会生成布尔值数组:

    arr1 = np.array([[2,4,9,12],[2,4,7,3]])
    print(arr<arr1) 

    [[False False True True]
    [ True False False False]]

     四基本的索引和切片

            当你将一个标量值赋值给一个切片时(如arr[5:8]=12),该值会自动传播(也就说后面将会讲到的“广播”)到整个选区。跟列表最重要的区别在于,数组切片是原始数组的视图。这意味着数据不会被复制,视图上的任何修改都会直接反映到源数组上。

            如果你想要得到的是ndarray切片的一份副本而非视图,就需要明确地进行复制操作,例如arr[5:8].copy()。

    (1)切片索引

    arr = np.array([0,  1,  2,  3,  4, 64, 64, 64,  8,  9])
    print(arr)
    print(arr[1:6])
    arr2d = np.array([[1, 2, 3],[4, 5, 6],[7, 8, 9]])
    print(arr2d)
    print(arr2d[1])
    print(arr2d[:2])
    print(arr2d[:,:2])
    

     

    [ 0 1 2 3 4 64 64 64 8 9]
    [ 1 2 3 4 64]


    [[1 2 3]
    [4 5 6]
    [7 8 9]]


    [4 5 6]


    [[1 2 3]
    [4 5 6]]


    [[1 2]
    [4 5]
    [7 8]]

    对切片表达式的赋值操作也会被扩散到整个选区

    (2)布尔型索引

    names = np.array(['Bob', 'Joe', 'Will', 'Bob', 'Will', 'Joe', 'Joe'])
    data = np.random.randn(7,4)
    print(names=='Bob')
    print(data[names == 'Bob'])
    #布尔型数组的长度必须跟被索引的轴长度一致。此外,还可以将布尔型数组跟切片、整数混合使用
    print(data[names == 'Bob',2:])
    print(data[names == 'Bob',2])
    print(data[names != 'Bob'])
    #~操作符用来反转条件很好用
    print(data[~(names == 'Bob')])
    #Python关键字and和or在布尔型数组中无效。要使用&与|。
    print((names == 'Bob')|(names == 'Will'))
    print(data[(names == 'Bob')|(names == 'Will')])
    #将data中的所有负值都设置为0
    data[data<0]=0
    print(data) 

    [ True False False True False False False]


    [[ 0.56947009 -0.61103578 -0.83001537 -1.03831856]
    [-0.72723257 0.72598221 0.36284245 -1.6662993 ]]


    [[-0.83001537 -1.03831856]
    [ 0.36284245 -1.6662993 ]]


    [-0.83001537 0.36284245]


    [[ 0.8576646 1.37711165 -0.97693128 0.70626358]
    [ 0.5193894 -1.07092886 -1.60173978 0.03837702]
    [ 0.25293635 0.09664311 2.20232715 0.44455463]
    [-0.4188091 -1.62252806 -1.435578 1.18620694]
    [-0.78747297 1.35354608 0.20774316 0.84989592]]


    [[ 0.8576646 1.37711165 -0.97693128 0.70626358]
    [ 0.5193894 -1.07092886 -1.60173978 0.03837702]
    [ 0.25293635 0.09664311 2.20232715 0.44455463]
    [-0.4188091 -1.62252806 -1.435578 1.18620694]
    [-0.78747297 1.35354608 0.20774316 0.84989592]]


    [ True False True True True False False]


    [[ 0.56947009 -0.61103578 -0.83001537 -1.03831856]
    [ 0.5193894 -1.07092886 -1.60173978 0.03837702]
    [-0.72723257 0.72598221 0.36284245 -1.6662993 ]
    [ 0.25293635 0.09664311 2.20232715 0.44455463]]


    [[0.56947009 0. 0. 0. ]
    [0.8576646 1.37711165 0. 0.70626358]
    [0.5193894 0. 0. 0.03837702]
    [0. 0.72598221 0.36284245 0. ]
    [0.25293635 0.09664311 2.20232715 0.44455463]
    [0. 0. 0. 1.18620694]
    [0. 1.35354608 0.20774316 0.84989592]]

    (3)花式索引

    利用整数数组进行索引,花式索引跟切片不一样,它总是将数据复制到新数组中。

    arr = np.empty((8,4))
    for i in range(8):
        arr[i] = i
    print(arr)
    print(arr[[1,2,4,0]]) 

    [[1. 1. 1. 1.]
    [2. 2. 2. 2.]
    [4. 4. 4. 4.]
    [0. 0. 0. 0.]]

    四、快速的元素级数组函数

    五、利用数组进行数据处理

     numpy.where(cond, xarr, yarr)函数是三元表达式x if condition else y的矢量化版本。np.where的第二个和第三个参数不必是数组,它们都可以是标量值。在数据分析工作中,where通常用于根据另一个数组而产生一个新的数组。

    arr = np.random.randn(3,4)
    print(arr)
    cond = arr>0
    print(cond)
    narr = np.where(cond,2,arr)
    print(narr)
    

      

    [[ 0.38456504 1.61308418 2.38985258 0.23335973]
    [-1.43672573 -1.29377899 -0.27695053 1.01830536]
    [-1.37364818 -1.17896878 0.32970775 1.34110048]]


    [[ True True True True]
    [False False False True]
    [False False True True]]


    [[ 2. 2. 2. 2. ]
    [-1.43672573 -1.29377899 -0.27695053 2. ]
    [-1.37364818 -1.17896878 2. 2. ]]

    数学和统计方法

    arr = np.random.randn(5, 4)
    arr.mean()
    arr.sum()
    arr.cumsum()
    arr.cumprod()
    

    排序

    顶级方法np.sort返回的是数组的已排序副本,而就地排序则会修改数组本身。  

    arr = np.random.randn(6)
    arr.sort()
    

    唯一化

    names = np.array(['Bob', 'Joe', 'Will', 'Bob', 'Will', 'Joe', 'Joe'])
    np.unique(names)
    

      

     
  • 相关阅读:
    xgqfrms™, xgqfrms® : xgqfrms's offical website of GitHub!
    xgqfrms™, xgqfrms® : xgqfrms's offical website of GitHub!
    xgqfrms™, xgqfrms® : xgqfrms's offical website of GitHub!
    xgqfrms™, xgqfrms® : xgqfrms's offical website of GitHub!
    【转】Vitalik:Layer-1 短期求创新,长期求保守
    扩容解决方案:状态通道
    以太坊的存储成本
    扩容解决方案:侧链
    区块链:Layer0 通用可扩展性解决方案
    实战演练丨Oracle死锁案例分析,看完你就懂了
  • 原文地址:https://www.cnblogs.com/yuhou/p/11124490.html
Copyright © 2011-2022 走看看