arrayproxy转numpy_Numpy基础知识

数据类型

1.数据类型之间的转换

5种基本类型:bool、int、uint、float、复数。

int32代表32位整型

在创建时指定类型的两种方式,直接类型 or 类型字符。

astype 改变数组的类型

直接a.dtype获取数组类型

>>> import numpy as np

>>> a=np.arange(12,dtype=float)

>>> a

array([ 0., 1., 2., 3., 4., 5., 6., 7., 8., 9., 10., 11.])

>>> a=np.arange(12,dtype='i')

>>> a

array([ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11], dtype=int32)

>>> a.dtype

dtype('int32')

>>> a.astype('float')

array([ 0., 1., 2., 3., 4., 5., 6., 7., 8., 9., 10., 11.])

2.数组标量

NumPy通常将数组元素作为数组标量返回(带有关联dtype的标量

3.溢出错误

当值需要比数据类型中的可用内存更多的内存时,NumPy数值类型的固定大小可能会导致溢出错误

#100的8次方超出32位存储空间

>>> np.power(100, 8, dtype=np.int64)

10000000000000000

>>> np.power(100, 8, dtype=np.int32)

1874919424

Python中的int大小是灵活的,不会溢出。

Numpy提供numpy.iinfo和numpy.finfo验证NumPy整数和浮点值的最小值或最大值

>>> np.finfo(float)

finfo(resolution=1e-15, min=-1.7976931348623157e+308, max=1.7976931348623157e+308, dtype=float64)

>>> np.iinfo(int)

iinfo(min=-2147483648, max=2147483647, dtype=int32)

>>> np.iinfo(np.int64)

iinfo(min=-9223372036854775808, max=9223372036854775807, dtype=int64)

如果64位整数仍然太小,则结果可能会转换为浮点数。浮点数提供了更大但不精确的可能值范围。

np.power(100,100,dtype=np.float64)

扩展精度

为了有效地进行内存的校准,np.longdouble通常以零位进行填充,即96或者128位, 哪个更有效率取决于硬件和开发环境;通常在32位系统上它们被填充到96位,而在64位系统上它们通常被填充到128位。

尽管它们的名称是这样叫的, 但是np.float96和np.float128只提供与np.longdouble一样的精度, 即大多数x86机器上的80位和标准Windows版本中的64位。

创建数组

1. 从其他Python结构(例如,列表,元组)转换

>>> a=np.array((1,2,3,4))

>>> a

array([1, 2, 3, 4])

>>> b=np.array([5,6,2])

>>> b

array([5, 6, 2])

>>> c = np.array([[1,2],(3,4)])

>>> c

array([[1, 2],

[3, 4]])

2. numpy原生数组的创建(例如,arange、ones、zeros等)

np.zeros((n,m)) 填充0

np.ones((n,m)) 填充1

#n,m代表数组的形状

np.linspace(n,m,p)

n为开始,p为结束,m为个数

3. 从磁盘读取数组,无论是标准格式还是自定义格式

使用 numpy.fromfile() 函数和 .tofile() 方法直接读取和写入numpy数组

4. 通过使用字符串或缓冲区从原始字节创建数组

5. 使用特殊库函数(例如,random)

Numpy输入与输出

使用genfromtxt导入数据

genfromtxt执行两个主要的循环。第一个循环以字符串序列转换文件的每一行。第二个循环将每个字符串转换为适当的数据类型

定义输入

唯一强制参数是数据的来源

将行拆分为列

delimiter为None的时候,按制表符分割

>>> from io import BytesIO

>>> data = b"1,2,3\n4,5,6"

>>> np.genfromtxt(BytesIO(data),delimiter=",")

array([[1., 2., 3.],

[4., 5., 6.]])

>>> data=b" 1 2 2"

>>> np.genfromtxt(BytesIO(data),delimiter=None)

array([1., 2., 2.])

delimiter为整数或数组时,可以规定输出的数组中每个列的宽度

>>> data=b"12345\n 3 4\n56 7"

>>> np.genfromtxt(BytesIO(data),delimiter=(3,2))

array([[123., 45.],

[ 3., 4.],

[ 56., 7.]])

#数组第一列宽为3,第二列宽为2

autostrip参数,为True时可消除每个元素的前导空白和尾随空白

comments可用于定义标记注释开始的字符串。默认情况下为#

>>> data=b"""#

... #comment

... #comment

... 1.2

... 3.4

... 5.6

... #commeng

... """

>>> np.genfromtxt(BytesIO(data),delimiter='.',comments="#")

array([[1., 2.],

[3., 4.],

[5., 6.]])

skip_header(n)和skip_footer(n)分别代表从头部和尾部跳过n个行

>>> data = "\n".join(str(i) for i in range(10))

>>> np.genfromtxt(BytesIO(data),)

array([ 0., 1., 2., 3., 4., 5., 6., 7., 8., 9.])

>>> np.genfromtxt(BytesIO(data),

... skip_header=3, skip_footer=5)

array([ 3., 4.])

usecols参数,截取部分列

>>> data = "1 2 3\n4 5 6"

>>> np.genfromtxt(BytesIO(data), usecols=(0, -1))

array([[ 1., 3.],

[ 4., 6.]])

#获取第一列和最后一列

设置名称

names参数,给列指定名称,可以用对应的列名来用usecols选出列。

>>> data=b"1 2 3\n4 5 6"

>>> np.genfromtxt(BytesIO(data),names="a,b,c",usecols=("a","c"))

array([(1., 3.), (4., 6.)], dtype=[('a', '

>>> np.genfromtxt(BytesIO(data),usecols=(0,-1))

array([[1., 3.],

[4., 6.]])

从数据本身定义列名,使用names关键字的值为True。这些名字将从第一行(在skip_header之后)被读取。

在函数中names参数具有最高优先级,优于其他方式定义的名称

defaultfmt参数

当names为None,默认为f0,f1等等。或names不够时,也是如此。

defaultfmt覆盖默认值

例:defaultfmt=“var_%i”

deletechars 删除列表

excludelist 排除列表

case_sensitive 大小写

选择数据的类型

接受一个dtype参数设置数据类型

一个包含两个键'names'和'formats'的字典。

现有的numpy.dtype对象。

特殊值None。在这种情况下,列的类型将根据数据本身确定(见下文)。

以下四点见代码

>>> np.genfromtxt(BytesIO(data),usecols=(0,-1),dtype=int)

array([[1, 3],

[4, 6]])

>>> np.genfromtxt(BytesIO(data),usecols=(0,-1),dtype='i4')

array([[1, 3],

[4, 6]])

>>> np.genfromtxt(BytesIO(data),names="a,b,c",dtype=[('a',int),('b',float)])

array([(1, 2.), (4, 5.)], dtype=[('a', '

>>> np.genfromtxt(BytesIO(data),names="a,b,c",dtype=(int,float,float))

array([(1, 2., 3.), (4, 5., 6.)],

dtype=[('a', '

除直接的dtype=int之外,其他的返回的都是一个带有结构化dtype的一维数组。

调整转换

converters定义转换函数。

converters参数必须是一个字典。

>>> data=b"1,2,3\n4,5,6\n"

>>> names="a,b,c"

>>> np.genfromtxt(BytesIO(data))

array([nan, nan])

>>> np.genfromtxt(BytesIO(data),delimiter=',')

array([[1., 2., 3.],

[4., 5., 6.]])

>>> np.genfromtxt(BytesIO(data),delimiter=',',names=names)

array([(1., 2., 3.), (4., 5., 6.)],

dtype=[('a', '

>>> def func(x):

... return '0'

...

>>>

np.genfromtxt(BytesIO(data),delimiter=',',dtype=int,names=names,converters={'b':func})

array([(1, 0, 3), (4, 0, 6)],

dtype=[('a', '

missing_values 和filling_values分别代表丢失值和为丢失值设定的值

usemask,布尔掩码,True为缺失

索引

切片索引

>>> y = np.arange(35).reshape(5,7)

>>> y

array([[ 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]])

>>> y[1:5:2,::3]

array([[ 7, 10, 13],

[21, 24, 27]])

索引数组

>>> x = np.arange(10,1,-1)

>>> x

array([10, 9, 8, 7, 6, 5, 4, 3, 2])

>>> x[np.array([3, 3, 1, 8])]

array([7, 7, 9, 2])

索引多维数组

>>> y[np.array([0,2,4]), np.array([0,1,2])]

array([ 0, 15, 30])

在这种情况下,如果索引数组具有匹配的形状,并且索引数组的每个维度都有一个索引数组,则结果数组具有与索引数组相同的形状

>>> y[np.array([0,2,4]), np.array([0,1])]

: shape mismatch: objects cannot be

broadcast to a single shape

如果索引数组的形状不同,则尝试将它们广播为相同的形状。如果它们无法广播到相同的形状,则会引发异常

>>> y[np.array([0,2,4]), 1]

array([ 1, 15, 29])

广播机制允许索引数组与其他索引的标量组合

可以仅使用索引数组对数组进行部分索引

>>> y[np.array([0,2,4])]

array([[ 0, 1, 2, 3, 4, 5, 6],

[14, 15, 16, 17, 18, 19, 20],

[28, 29, 30, 31, 32, 33, 34]])

布尔或掩码索引数组

布尔数组做索引返回的是一维数组

>>> b = y>20

>>> y[b]

array([21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34])

>>> b[:,5]

array([False, False, False, True, True])

>>> y[b[:,5]]

array([[21, 22, 23, 24, 25, 26, 27],

[28, 29, 30, 31, 32, 33, 34]])

#此时的b[:,5]相当于【3,4】

布尔索引要和被索引数组的形状完全相同才能索引到每一个元素。

如果布尔索引少一个维度,那么对数组进行索引时的最小单位就上升一个维度。

>>> x

array([[[ 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]]])

>>> a=np.array([True,True,False,True,False])

>>> a

array([ True, True, False, True, False])

>>> b=np.array([[a,a,a],[a,a,a]])

>>> b

array([[[ True, True, False, True, False],

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

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

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

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

[ True, True, False, True, False]]])

>>> x[b]

array([ 0, 1, 3, 5, 6, 8, 10, 11, 13, 15, 16, 18, 20, 21, 23, 25, 26,

28])

在程序中使用索引

slice 切片

Ellipsis 省略号

>>> indices = (1,1,1,1)

>>> z[indices]

40

>>> indices = (1,1,1,slice(0,2)) # same as [1,1,1,0:2]

>>> z[indices]

array([39, 40])

>>> indices = (1, Ellipsis, 1) # same as [1,...,1]

>>> z[indices]

array([[28, 31, 34],

[37, 40, 43],

[46, 49, 52]])

广播

术语广播(Broadcasting)描述了 numpy 如何在算术运算期间处理具有不同形状的数组

当一个数组和一个标量值在一个操作中组合时,会发生最简单的广播

>>> a = np.array([1.0, 2.0, 3.0])

>>> b = 2.0

>>> a * b

array([ 2., 4., 6.])

一般广播规则

在两个数组上运行时,NumPy会逐元素地比较它们的形状。它从尾随尺寸开始,并向前发展。两个尺寸兼容时

1.他们是平等的,或者

2.其中一个是1

平等的意味着

1.有相同的形状

2.最外围的元素个数相同

例:a和b最外围都是3个

>>> import numpy as np

>>> a=np.array([[1,2,3],[3,4,5],[5,6,7]])

>>> b=np.array([1,2,3]),

>>> a*b

array([[ 1, 4, 9],

[ 3, 8, 15],

[ 5, 12, 21]])

各种情况

A (2d array): 5 x 4

B (1d array): 1

Result (2d array): 5 x 4

A (2d array): 5 x 4

B (1d array): 4

Result (2d array): 5 x 4

A (3d array): 15 x 3 x 5

B (3d array): 15 x 1 x 5

Result (3d array): 15 x 3 x 5

A (3d array): 15 x 3 x 5

B (2d array): 3 x 5

Result (3d array): 15 x 3 x 5

A (3d array): 15 x 3 x 5

B (2d array): 3 x 1

Result (3d array): 15 x 3 x 5

>>> x = np.arange(4)

>>> xx = x.reshape(4,1)

>>> y = np.ones(5)

>>> z = np.ones((3,4))

>>> x.shape

(4,)

>>> y.shape

(5,)

>>> x + y

ValueError: operands could not be broadcast together with shapes (4,) (5,)

>>> xx.shape

(4, 1)

>>> y.shape

(5,)

>>> (xx + y).shape

(4, 5)

>>> xx + y

array([[ 1., 1., 1., 1., 1.],

[ 2., 2., 2., 2., 2.],

[ 3., 3., 3., 3., 3.],

[ 4., 4., 4., 4., 4.]])

>>> x.shape

(4,)

>>> z.shape

(3, 4)

>>> (x + z).shape

(3, 4)

>>> x + z

array([[ 1., 2., 3., 4.],

[ 1., 2., 3., 4.],

[ 1., 2., 3., 4.]])

>>> a = np.array([0.0, 10.0, 20.0, 30.0])

>>> b = np.array([1.0, 2.0, 3.0])

>>> a[:, np.newaxis] + b

array([[ 1., 2., 3.],

[ 11., 12., 13.],

[ 21., 22., 23.],

[ 31., 32., 33.]])

字节交换

字节排序和ndarrays

ndarray是一个为内存中的数据提供python数组接口的对象

关于一些2字节整数与4字节整数之间的转换之类的。

更改数组dtype中的字节顺序信息,以便将基础数据解释为不同的字节顺序。这是作用 arr.newbyteorder()

更改基础数据的字节顺序,保留dtype解释。这是做什么的 arr.byteswap()

dtype参数很重要

结构化数组

结构化数组,ndarray。包含dtype,一个一维数组,元素是元组。

>>> import numpy as np

>>> x = np.array([('李栋良',22,84),('Daenerys',22,55)],

... dtype=[('name','U10'),('age','i4'),('weight','f4')]

...

...

... )

>>> x

array([('李栋良', 22, 84.), ('Daenerys', 22, 55.)],

dtype=[('name', '

>>> x[name]

Traceback (most recent call last):

File "", line 1, in

NameError: name 'name' is not defined

>>> x['name']

array(['李栋良', 'Daenerys'], dtype='

>>> x['age']=23

>>> x

array([('李栋良', 23, 84.), ('Daenerys', 23, 55.)],

dtype=[('name', '

>>> x['weight'][1]=54

>>> x

array([('李栋良', 23, 84.), ('Daenerys', 23, 54.)],

dtype=[('name', '

结构化数据类型创建

元组列表的形式,shape是可选的

np.dtype([('x', 'f4'), ('y', np.float32), ('z', 'f4', (2, 2))])

逗号分隔,字段名称被赋予默认名称 f0、f1等

np.dtype('i8, f4, S3')

dtype([('f0', '

字段参数组字典

字典有两个必需键 “names” 和 “format”,以及四个可选键 “offsets”、“itemsize”、“Aligned” 和 “title”。

>>> np.dtype({'names':['A','B'],'formats':['i4','f4']})

dtype([('A', '

可以通过names使用相同长度的字符串序列分配属性来修改字段名称。

dtype对象还具有类似字典的属性,fields其键是字段名称, 其值是包含每个字段的dtype和字节偏移量的元组。

>>> d.fields

mappingproxy({'x': (dtype('int64'), 0), 'y': (dtype('float32'), 8)})

偏移量指的是内存中的偏移,可以认为指定,也可以自动偏移和对齐。

默认情况下(align=False),numpy将字段打包在一起,使得每个字段从前一个字段结束的字节偏移开始,并且字段在内存中是连续的

>>> d=np.dtype('u1,i8,f4,u2,u1,i4')

>>> d.fields

mappingproxy({'f0': (dtype('uint8'), 0), 'f1': (dtype('int64'), 1), 'f2': (dtype('float32'), 9), 'f3': (dtype('uint16'), 13), 'f4': (dtype('uint8'), 15), 'f5': (dtype('int32'), 16)})

>>> [d.fields[name][1] for name in d.names]

[0, 1, 9, 13, 15, 16]

如果align=True设置了,numpy将以与许多C编译器填充C结构相同的方式填充结构

>>> d=np.dtype('u1,i8,f4,u2,u1,i4',align=True)

>>> [d.fields[name][1] for name in d.names]

[0, 8, 16, 20, 22, 24]

索引和分配给结构化数组

使用元组赋值

使用标量赋值,会将标量分配给所有字段

>>> x=np.array(2,dtype='i4,u1')

>>> x

array((2, 2), dtype=[('f0', '

来自其他结构化数组的赋值是可以的。但是具有不同数量的字段的结构化数组不能彼此分配

索引

使用名称索引和修改

访问的字段是子数组,则子数组的维度将附加到结果的形状

>>> x = np.zeros((2, 2), dtype=[('a', np.int32), ('b', np.float64, (3, 3))])

>>> x

array([[(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.]])]],

dtype=[('a', '

>>> x['a'].shape

(2, 2)

>>> x['b'].shape

(2, 2, 3, 3)

结构化数组中的名称可看作列名

>>> a=np.zeros(3)

>>> a

array([0., 0., 0.])

>>> a=np.zeros(3, dtype=[('a', 'i4'), ('b', 'i4'), ('c', 'f4')])

>>> a

array([(0, 0, 0.), (0, 0, 0.), (0, 0, 0.)],

dtype=[('a', '

>>> a[['a','c']]

array([(0, 0.), (0, 0.), (0, 0.)],

dtype={'names':['a','c'], 'formats':['

使用整数进行索引获得结构化标量,获得的结构化标量也像视图一样,进行修改会修改原数组

结构比较

>>> a=np.ones(2,dtype='i4,u1')

>>> a

array([(1, 1), (1, 1)], dtype=[('f0', '

>>> b=np.ones(2,dtype='i4,u1')

>>> a==b

array([ True, True])

记录数组

记录数组允许暗属性访问结构化数组的字段

你可能感兴趣的:(arrayproxy转numpy_Numpy基础知识)