python numpy(二)

python numpy(二)

这一节是精华需要好好吸收。
阅读需15min。事件需30min。
在这里插入图片描述


前言

在理解了前一节的基础操作之后。我们发现一个问题,好像没什么卵用?
用不到具体的情形中去!!!
因为我们的数据来源于上游的分析,而不是来源于我们的样例里面随意的初始化。

所以想要利用ndarray处理上游的数据,我们就需要进行两个大的操作。

  1. 将上游的数据转化为ndarray
  2. 索引数据,因为没有访问,谈何处理?

一、数据类型的转化

数组list

array和asarray方法都是常用的
import numpy as np 
a = np.array([1, 2, 3, 4, 5])  
print (a)
a = np.array([1, 2, 3, 4, 5], ndmin =  2)  
print (a)

你会惊喜的发现括号的个数不一样
那是当然的,维度不一样的嘛。

维度这么理解呢?
你可以自行的百度,不过我可以给一个直观化的认识那就是,括号的最大层数
这个概念无法理解,因为人只对前三维有意义化的认识。后面的都算是纯数学推演,所以无需理解。
形式就完了。

a = np.array([[1,  2],  [3,  4]])  
print (a)

可以无限嵌套,但是最好不要超过三层,不然烧脑。。。

元组

和列表一样
x =  (1,2,3) 
a = np.asarray(x)  
print (a)

元组列表

和列表一样,但是不会递归

x =  [(1,2,3),(4,5)] 
a = np.asarray(x)  
print (a) # [(1, 2, 3) (4, 5)]

字典

x =  {1:"tangseng",2:"wukong"}
a = np.asarray(x)  
print (a) # {1:"tangseng",2:"wukong"},实际无法操作

ndarray实际上并不是为了处理关联数据的,所以意义不大。

反向转化只需要使用list(),tuple()。

frombuffer

numpy.frombuffer 接受 buffer 输入参数,以流的形式读入转化成 ndarray 对象
numpy.frombuffer(buffer, dtype = float, count = -1, offset = 0)
import numpy as np 
 
s =  b'Hello World' 
a = np.frombuffer(s, dtype =  'S1')  
print (a) # [b'H' b'e' b'l' b'l' b'o' b' ' b'W' b'o' b'r' b'l' b'd']

buffer里面的都是二进制的数据,需要注意一下。

fromiter

numpy.fromiter 方法从可迭代对象中建立 ndarray 对象,返回一维数组
numpy.fromiter(iterable, dtype, count=-1)
import numpy as np 
 
# 使用 range 函数创建列表对象  
list=range(5)
it=iter(list)
 
# 使用迭代器创建 ndarray 
x=np.fromiter(it, dtype=float)
print(x)

鉴于python之中的迭代器还是比较好理解和实现的,所以有必要了解一下。
不过本身迭代器在实现中过程中也会追求和list一致,所以很多时候迭代器可以当做列表处理。。。
你可以猜啊,妙不妙?

二、ndarray的索引,切片

索引和切片都是为了获得某个位置或者是某一段数据的内容。 

重中之重!!!

1.索引

import numpy as np
 
a = np.arange(1,10)
print(a)
print(a[0])
print(a[::-1]) # 反向输出
a = a.reshape((3,3)) # 注意是传入的元组
print(a)
print(a[0])
print(a[:,-1]) # 最右边的列
# 结果
[1 2 3 4 5 6 7 8 9]
1
[9 8 7 6 5 4 3 2 1]
[[1 2 3]
 [4 5 6]
 [7 8 9]]
[1 2 3]
[3 6 9]

解释一下::-1是一个简写,第一个:之前是起点位置,没有写,默认是开头,第二个:之前是结尾,也省略了,默认是整体结尾
还记得上一讲的拷贝吗?[:]。最后一个参数是step可以是负数,从右向左。

麻雀虽小,五脏俱全。。。

2.切片

主要是二维及以上

代码如下(示例):

import numpy as np
 
a = np.array([[1,2,3],[3,4,5],[4,5,6]])  
print (a[:,1])
print (a[...,1])   # 第2列元素
print (a[1,:]) 
print (a[1,...])   # 第2行元素
print (a[...,1:])  # 第2列及剩下的所有元素
两种写法都可以,更建议用:以便于和list,pandas统一吧。而且有的时候只要部分的列:显然更好一点

三,高级索引

NumPy 比一般的 Python 序列提供更多的索引方式。除了之前看到的用整数和切片的索引外,数组可以由整数数组索引、布尔索引及花式索引。

像这么秀的东西也只有比较底层的向量运算才用的到。。。但要知道这些骚操作。

在这里插入图片描述

列表索引

import numpy as np 
 
x = np.array([[1,  2],  [3,  4],  [5,  6]]) 
y = x[[0,1,2],  [0,1,0]]  # 前一个索引用的列表代表横坐标,后面代表纵坐标。从左上角开始
print (y)
import numpy as np 
 
x = np.array([[  0,  1,  2],[  3,  4,  5],[  6,  7,  8],[  9,  10,  11]])  
print ('我们的数组是:' )
print (x)
print ('n')
rows = np.array([[0,0],[3,3]]) 
cols = np.array([[0,2],[0,2]]) 
y = x[rows,cols]  
print  ('这个数组的四个角元素是:')
print (y)

布尔索引

比较常用,相当于是向量化的if筛选,一般结合np的is函数使用
import numpy as np 
 
x = np.array([[  0,  1,  2],[  3,  4,  5],[  6,  7,  8],[  9,  10,  11]])  
print ('我们的数组是:')
print (x)
print ('n')
# 现在我们会打印出大于 5 的元素  
print  ('大于 5 的元素是:')
print (x[x >  5])
print(x[(x > 5) & (x < 10)]) # 要加小括号,[]里面的语法不太灵活,比较严格
a = np.array([np.nan,  1,2,np.nan,3,4,5])  
print (a[~np.isnan(a)]) # ~ 相当于not取反

a = np.array([1,  2+6j,  5,  3.5+5j])  
print (a[np.iscomplex(a)])

可以更加个性化筛选条件

a = np.array([[1, 1, 0],
                    [2, 1, 0],
                    [3, 2, 0],
                    [4, 2, 0],
                    [5, 3, 0]])
b=a[(a[...,0]>2) & (a[...,1]<3),...]  # 此行的最后的逗号和省略号可以省略

花式索引

花式索引指的是利用整数数组进行索引。
花式索引跟切片不一样,它总是将数据复制到新数组中.
import numpy as np 
 
x=np.arange(32).reshape((8,4))
print (x[[4,2,1,7]]) # 列表里是新的行号顺序
x=np.arange(32).reshape((8,4))
print (x[[-4,-2,-1,-7]]) # 也可以负数
列表索引往往用来做高维的切片,布尔索引可以认为是筛选,花式索引一般用来复制

四,总结

都是比较重要的。所以多加练习吧,同志们。

需要注意一些地方。

  1. 引用和复制的判断问题,如果左右两个一模一样,np为了节省内存就是引用。有了差别哪怕数据类型上不同都会创建新的。
  2. 切片是提取数据的最基本的方式。
  3. bool索引的本质就是向量化的if筛选或者filter。有兴趣可以用列表表达式模拟该过程。

我需要一键三连!!!

在这里插入图片描述

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
THE END
分享
二维码
< <上一篇
下一篇>>