ndarray数组

ndarray数组

import numpy as np
# Numpy数组是同质数组,即所有元素的数据类型必须相同,下标从0开始
ary = np.array([1, 2, 3, 4, 5, 6])
print(ary, type(ary))  # 输出一维数组以及其数据类型
print(ary.shape)  # 输出维度 (6,):表示有六个元素的一维元素
ary.shape = (2, 3)  # 改变维度为两行三列,元素个数要符合维度空间元素个数,否则会报错
print(ary, ary.shape)  # [[1 2 3] [4 5 6]] (2, 3)
ary.shape = (6,)
# 数组的运算
print(ary * 3)  # 每个元素都乘三倍,加减乘除都应用
print(ary > 3)  # 每个元素进行布尔运算,返回布尔值
print(ary - ary)  # 两个数组对应位置元素进行运算,维度需要一致

ndarray在内存中存储:元数据+实际数据

优点:将实际数据与元数据分开存放,一方面提高内存空间的使用效率;另一方面减少对实际数据的访问频率,提高性能。

  • 元数据:存储对目标数组的描述信息,比如dim(维数),size(元素个数),shape(维度),dtype(实际存储的数据类型)…
  • 实际数据:完整的数组数据

ndarray数组的创建

import numpy as np
# 创建ndarray对象形式
a = np.array([[1, 2, 3],
              [4, 5, 6]])
# size:输出最基本的元素个数;length:最外层的包含元素个数
print(a, 'size:', a.size, 'length:', len(a))  # [1,2,3] [4,5,6] size:6 length:2
b = np.arange(0, 5, 1)  # arange(起始值,终止值,步长)
print(b)  # 0 1 2 3 4
c = np.arange(0, 36, 2)
print(c)  # [ 0  2  4  6  8 10 12 14 16 18 20 22 24 26 28 30 32 34]
c.shape = (3, 2, 3)  # 将一维变成三维 (页/行/列)
print(c)
"""
[[[ 0  2  4]
  [ 6  8  10]]

 [[12 14 16]
  [18 20 22]]

 [[24 26 28]
  [30 32 34]]]
"""
# 索引下标
print(c[0])  # 第一页 [[ 0  2  4] [ 6  8  10]]
print(c[0][1])  # 第一页的第二行 [ 6  8  10]
print(c[0][1][2])  # 第一页第二行的第三列 10 print(c[0,1,2])
d = np.zeros(3, dtype=float)  # zeros(数组元素个数,dtype='类型')所有元素值为0
print(d, d.dtype)  # 0. 0. 0. float64
# d.dtype = int 0 0 0 0 0 0 int32 错误的修改类型方式
d = d.astype(int)
print(d, d.dtype)  # 0 0 0 int32
e = np.ones(3, bool)
print(e)  # True True True

Numpy基本数据类型

类型名类型表示符
布尔型bool
有符号整数型int8(-128~127)/int16/int32
无符号整数型uint8(0~255)/uint16/uint32
浮点型float16/float32/float64
复数型complex64/complex128
字串型str,每个字符用32位Unicode编码表示

自定义符合类型

类型字符码简写

类型字符码
bool?
int8/16/32/64i1/i2/i4/i8
uint8/16/32/64u1/u2/u4/u8
float16/32/64f2/f4/f8
complex64/128c8/c16
strU<字符数>
datetime64M8[Y]/[M]/[D]/[h]/[m]/[s]

字节序前缀:用于多字节整数和字符串

前缀含义
<小端
>大端
[=]硬件字节序

存储复合类型

import numpy as np
# 自定义复合类型(前三种较为常用)
data = [
    ('one', [90, 80, 70], 11),
    ('two', [95, 85, 75], 12),
    ('three', [100, 100, 100], 13)
]  # 学生列表[名字,成绩[语文,数学,英语],年龄]
students_one = np.array(data, dtype='U5,3int32,int32')
# 第一种设置dtype的方式
# U5 Unicode字符最多有5个
# 3int32 int32的元组中有3个元素
# int32 最后一个元素是int32类型的
print(students_one)
# 第二种设置dtype的方式-元组
students_two = np.array(data, dtype=[('name', 'str', 5),
                                     ('score', 'int32', 3),
                                     ('age', 'int32')])
print('name=', students_two[2]['name'], 'age=', students_two[2]['age'])  # name= three age= 13
# 第三种设置dtype的方式-字典
students_three = np.array(data, dtype={'names': ['name', 'score', 'age'],
                                       'formats': ['U5', '3int32', 'int32']})
print(students_three[1]['score'])
# 第四种设置dtype的方式 最后的数字代表字节偏移量
students_four = np.array(data, dtype={'names': ('U5', 0),
                                      'scores': ('3int32', 20),
                                      'ages': ('int32', 32)})
print(students_four)
# 第五种设置dtype的方式-大小端方式

# 数组中存储日期数据类型
times = ['2000-12-25', '2000', '2000-12',
         '2012-01-01', '2022-02-22 22:22:22']
date = np.array(times)
print(date, date.dtype)
# ['2000-12-25' '2000' '2000-12' '2012-01-01' '2022-02-22 22:22:22'] <U19
date = date.astype('M8[D]')  # 时间精确到 yyyy-MM-DD
print(date, date.dtype)
# ['2000-12-25' '2000-01-01' '2000-12-01' '2012-01-01' '2022-02-22'] datetime64[D]
print(date[0] - date[2])  # 时间间隔

数组对象的维度操作

import numpy as np
a = np.arange(1, 10)
print(a, a.shape)  # [1 2 3 4 5 6 7 8 9] (9,)
# 视图变维(数据共享):reshape() && ravel()
b = a.reshape(3, 3)  # 三行三列
print(a, '→a')
a[0] = 999
print(b, '→b')  # b随着a中内容的变化而变化
print(b.ravel())  # 抻平
# 复制变维(数据独立):flatten()
c = b.flatten()
print(c, '→c')
b[0][0] = 888
print(a, '→a')
print(b, '→b')
print(c, '→c')  # a,b俩数据共享;c不随着其改变,只保留复制的部分
# 就地变维:shape()没有返回值 resize()
c.shape = (3, 3)
print(c, '→c')  # 变成三行三列
c.resize((9,))
print(c, '→c')  # 变为一维数组

ndarray数组切片:数组对象[起始位置:终止位置:步长,…]

import numpy as np
# 一维数组切片
a = np.arange(1, 10)
print(a)  # [1 2 3 4 5 6 7 8 9]
print(a[:3])  # [1 2 3]默认从0开始切到下标3(不包括)为止
print(a[3:6])  # [4 5 6]从下标3切到下标6(不包括)为止
print(a[6:])  # [7 8 9]从下标6开始到结尾
print(a[::-1])  # [9 8 7 6 5 4 3 2 1]从尾部开始切到首部
print(a[:-4:-1])  # [9 8 7]从尾部开始切到倒数第四个(不包括)
print(a[-7::-1])  # [3 2 1]从倒数第七个开始切到首部
print(a[::])  # [1 2 3 4 5 6 7 8 9]
print(a[:])  # [1 2 3 4 5 6 7 8 9]
print(a[2::3])  # [3 6 9]从下标3开始往后步长为3的切
# 二维数组的切片
a.resize(3, 3)  # 变为三行三列的二维数组
print(a[:2, :2])  # 前两行的前两列切片[[1 2][4 5]]
print(a[1::2, ::2])  # [[4 6]]下标为1的行开始切,步长为2;从0列开始切,步长为2
# 多维数组的切片,每个维度用','隔开切片

ndarray数组的掩码操作

import numpy as np
# 掩码操作
a = np.arange(1, 10)
mask = [True, False, True, False, True, False, True, False, True]
print(a[mask])  # 显示对应位置为True的数组元素
a = np.arange(100)  # 0~99
print(a[(a % 3 == 0)&(a % 7 == 0)])  # 寻找0~99中既是3的倍数又是7的倍数的元素
# 基于索引的排序
test = np.array(['second', 'fourth', 'fifth', 'first', 'third'])
rank = [3, 0, 4, 1, 2]  # 排序索引
print(test[rank])

多维数组的组合与拆分

水平方向上的操作

import numpy as np
# 多维数组的组合与拆分
a = np.arange(1, 7).reshape(2, 3)
b = np.arange(7, 13).reshape(2, 3)
print(a, '→a')  # [[1 2 3][4 5 6]]
print(b, '→b')  # [[ 7  8  9][10 11 12]]
# 水平组合
c = np.hstack((a, b))
print(c, '→c')  # [[ 1  2  3  7  8  9][ 4  5  6 10 11 12]]
# 水平拆分
a, b, c = np.hsplit(c, 3)  # 水平拆分三部分并各自存放在a,b,c中
print(a, '→a')  # [[1 2][4 5]]
print(b, '→b')  # [[3  7][6 10]]
print(c, '→c')  # [[8  9][11 12]]

垂直方向上的操作

import numpy as np
# 垂直方向操作
c = np.vstack((a, b))
print(c, '→c')  # [[ 1  2  3][ 4  5  6][ 7  8  9][10 11 12]] →c
a, b = np.vsplit(c, 2)
print(a, '→a')  # [[1 2 3][4 5 6]]
print(b, '→b')  # [[ 7  8  9][10 11 12]]

深度方向上的操作

import numpy as np
# 深度方向操作
c = np.dstack((a, b))
# 2页x3行x2列的三维数组
print(c, '→c')  # [[[ 1  7][ 2  8][ 3  9]]  [[ 4 10][ 5 11][ 6 12]]] →c
a, b = np.dsplit(c, 2)
# 2页x3行x1列的三维数组
print(a, '→a')  # [[[1][2][3]]  [[4][5][6]]] →a
print(b, '→b')  # [[[7][8][9]]  [[10][11][12]]] →b

相关函数

import numpy as np
# 通过axis作为关键字参数指定组合的方向
    # axis:0(垂直方向组合)/1(水平方向组合)/2(深度方向组合)
    # 只有三维数组才能进行深度方向组合
np.concatenate((a, b), axis=?)
# 通过给出的数组与要拆分的份数,按照axis值进行方向上的拆分
np.spilt(c,2,axis=?)

# 长度不等的数组组合
a = np.array([1, 2, 3, 4, 5])
b = np.array([1, 2, 3])
# 填充b数组使其长度与a相同
b = np.pad(b, pad_width=(0, 2), mode='constant',
           constant_values=-1)
# pad_width=(0, 2) 0表示往头部填充0个元素,2表示往尾部填充2个元素
# mode='constant' 表示以常量的形式填充
# constant_values=-1 填充的值是-1
print(b)  # [ 1  2  3 -1 -1]

简单的一维数组组合方式

import numpy as np
a = np.arange(1, 6)
b = np.arange(6, 11)
c = np.row_stack((a, b))  # 把两个一维数组变成两行
print(c)  # [[ 1  2  3  4  5][ 6  7  8  9 10]]
d = np.column_stack((a, b))  # 把两个一维数组变成两列
print(d)  # [[ 1  6][ 2  7][ 3  8][ 4  9][ 5 10]]

ndarray类的其他属性

  • shape: 维度
  • dtype: 元素类型
  • size: 元素数量
  • ndim: 维数,len(shape)
  • itemsize: 元素字节数
  • nbytes: 总字节数=size*itemsize
  • real: 复数数组的实部数组
  • imag: 复数数组的虚部数组
  • T: 数组对象的转置视图
  • flat: 扁平迭代器
import numpy as np
a = np.array([[1 + 1j, 2 + 4j, 3 + 7j],
              [4 + 2j, 5 + 5j, 6 + 8j],
              [7 + 3j, 8 + 6j, 9 + 9j]])
print(a.shape)  # (3, 3)
print(a.dtype)  # complex128
print(a.ndim)  # 2
print(a.size)  # 9
print(a.itemsize)  # 16
print(a.nbytes)  # 144
print(a.real, a.imag, sep='\n')  # 打印实部/虚部
print(a.T)  # 转置
print([elem for elem in a.flat])  # 抻平
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值