python:numpy陣列運算、排序、統計、隨機數生成
主要內容
1) 利用陣列進行資料處理
2) 將條件邏輯表述為陣列運算
3) 數學與統計方法
4) 用於布林型陣列的方法
5) 排序
6) 唯一化以及其他的集合邏輯
7) 用於陣列的檔案輸入輸出
8) 線性代數
1) 利用陣列進行資料處理
import numpy as np
points = np.arange(-5,5,1)
print points
xs,ys = np.meshgrid(points,points)
ys
[-5 -4 -3 -2 -1 0 1 2 3 4]
array([[-5, -5, -5, -5, -5, -5, -5, -5, -5, -5],
[-4, -4, -4, -4, -4, -4, -4, -4, -4, -4],
[-3, -3, -3, -3, -3, -3, -3, -3, -3, -3],
[-2, -2, -2, -2, -2, -2, -2, -2, -2, -2],
[-1, -1, -1, -1, -1, -1, -1, -1, -1, -1],
[ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
[ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
[ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2],
[ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3],
[ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4]])
xs
array([[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4],
[-5, -4, -3, -2, -1, 0, 1, 2, 3, 4]])
2) 將條件邏輯表述維陣列運算
np.where()函式是三元表示式:x if condition else y 的向量化版本,假設,我們有一個布林陣列和兩個陣列
xarr = np.array([1,2,3,4,5])
yarr = np.array([6,7,8,9,10])
cond = np.array([True,False,True,True,False,])
加入我們想根據cond陣列的情況來選取xarr或yarr陣列中的值,有兩種方法,一種是列表推導式,另外一種是向量化
##列表推導式
%timeit result = [(x if c else y) for x,y,c in zip(xarr,yarr,cond)]
The slowest run took 14.83 times longer than the fastest. This could mean that an intermediate result is being cached.
1000000 loops, best of 3: 1.77 µs per loop
result
[1, 7, 3, 4, 10]
## 向量化
%timeit result = np.where(cond,xarr,yarr)
The slowest run took 13.14 times longer than the fastest. This could mean that an intermediate result is being cached.
1000000 loops, best of 3: 827 ns per loop
result
array([ 1, 7, 3, 4, 10])
從上述結果真可以看出,向量化的計算速度大概是列表計算的三倍,注意返回結果型別的不一致!np.where函式的引數還可以是標量
arr = np.random.randn(4,4)
arr
array([[ 0.81362115, -0.59091357, 0.04834518, 0.31279457],
[ 0.14034937, -0.495634 , -1.65939013, -0.06717819],
[ 1.27779012, 1.00333966, -1.89590419, 0.06417592],
[-0.39706132, -0.55924097, 0.19493047, -2.09199616]])
np.where(arr>0,2,-2)
array([[ 2, -2, 2, 2],
[ 2, -2, -2, -2],
[ 2, 2, -2, 2],
[-2, -2, 2, -2]])
arr
array([[ 0.81362115, -0.59091357, 0.04834518, 0.31279457],
[ 0.14034937, -0.495634 , -1.65939013, -0.06717819],
[ 1.27779012, 1.00333966, -1.89590419, 0.06417592],
[-0.39706132, -0.55924097, 0.19493047, -2.09199616]])
注意,條件邏輯表示式不改變原陣列
np.where(arr>0,2,arr)#只在條件為真是做出改變
array([[-1.05581125, -0.33226037, 2. , -0.35399731],
[ 2. , -0.85778503, 2. , -0.63576095],
[ 2. , 2. , -0.76836718, 2. ],
[-0.04934349, -0.95880935, 2. , -1.00340544]])
還可以巢狀
cond1 = np.array([True,False,True,True,True,])
np.where(cond & cond1,0,np.where(cond1,1,2))
array([0, 2, 0, 0, 1])
另外,布林型資料還可以在計算過程中被當做0或1處理
result = 1*(cond - cond1) + 2*(cond+cond1)
C:\Program Files\anaconda\lib\site-packages\ipykernel\__main__.py:1: DeprecationWarning: numpy boolean subtract, the `-` operator, is deprecated, use the bitwise_xor, the `^` operator, or the logical_xor function instead.
if __name__ == '__main__':
result
array([2, 0, 2, 2, 3])
3)數學和統計方法
比如sum、mean、std等聚合計算(aggregation,通常叫做約減(reduction)),既可以當做陣列的例項方法呼叫(array.sum()),還可以當做頂級Numpy函式使用sum(array)。
arr = np.ones((4,5))
arr
array([[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.]])
arr.mean()
1.0
np.mean(arr)
1.0
arr.sum()
20.0
arr
array([[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.]])
注意,聚合函式不改變原陣列
np.sum(arr)
20.0
arr[:,2] = 2
arr
array([[ 1., 1., 2., 1., 1.],
[ 1., 1., 2., 1., 1.],
[ 1., 1., 2., 1., 1.],
[ 1., 1., 2., 1., 1.]])
arr.sum(0)#縱軸方向\
13
arr
array([0, 1, 3, 4, 5])
arr.sum(1)#橫軸方向
array([ 6., 6., 6., 6.])
arr.cumsum(0)#縱軸方向的累計和,放回新陣列
array([[ 1., 1., 1., 1., 1.],
[ 2., 2., 2., 2., 2.],
[ 3., 3., 3., 3., 3.],
[ 4., 4., 4., 4., 4.]])
基本陣列統計方法
方法 | 說明 |
---|---|
sum | 對陣列中全部或某軸向的元素求和,0長度的陣列的sum為0 |
mean | 算數平均數,0長度的陣列的mean為NaN |
std、var | 標準差、方差,自由度可調(預設為n) |
min、max | 最大和最小 |
argmin、argmax | 最大和最小的索引 |
cumsum、cumprod | 所有元素的累計和、累計積 |
4) 用於布林型陣列的方法
1) sum 統計布林型陣列中True的個數,由於布林型陣列中True會被當成1來參加運算。
2) any 用於測試陣列中是否存在一個或多個True
3) all 用來檢查陣列中所有值是否都是True
4) 另外 any、all也可以用與非布林型陣列,所有非0元素會被當做True
import numpy as np
bools = np.array([False,False,True,False,True])
bools.sum()
2
bools.any()
True
bools.all()
False
從上述結果中,any和all說明bools中有True但不全是,而sum統計了True的個數。
5)排序
arr = np.arange(5)
arr[2]=5
arr
array([0, 1, 5, 3, 4])
arr.sort()
arr
array([0, 1, 3, 4, 5])
np.sort(arr)
array([0, 1, 3, 4, 5])
array = np.arange(1,5,0.5).reshape(2,4)
array
array([[ 1. , 1.5, 2. , 2.5],
[ 3. , 3.5, 4. , 4.5]])
array[:,1] = np.array([3.5,1.5]).T
array
array([[ 1. , 3.5, 2. , 2.5],
[ 3. , 1.5, 4. , 4.5]])
array.sort(0)#在縱軸上排序
array
array([[ 1. , 1.5, 2. , 2.5],
[ 3. , 3.5, 4. , 4.5]])
array[:,1] = np.array([3.5,1.5]).T
print array
array.sort(1)#在橫軸上排序
array
[[ 1. 3.5 2. 2.5]
[ 3. 1.5 4. 4.5]]
array([[ 1. , 2. , 2.5, 3.5],
[ 1.5, 3. , 4. , 4.5]])
python內建排序程式
array = np.array([1,2,6,3,5,4])
array
array([1, 2, 6, 3, 5, 4])
sorted(array)#python內建一般返回列表
[1, 2, 3, 4, 5, 6]
array#內建不改變原來是陣列?
array([1, 2, 6, 3, 5, 4])
注意,sort會在原陣列上做修改
6) 唯一化以及其他的集合邏輯
numpy提供一些針對**一維**ndarray的基本集合運算,最常用的是np.unique(),它用於找出陣列中的唯一值並返回已排序的結果
names = np.array(['a','b','c','a','c'])
names
array(['a', 'b', 'c', 'a', 'c'],
dtype='|S1')
np.unique(names)
array(['a', 'b', 'c'],
dtype='|S1')
names
array(['a', 'b', 'c', 'a', 'c'],
dtype='|S1')
ints = np.array([3,3,3,2,2,2,1,1,4,4])
ints
array([3, 3, 3, 2, 2, 2, 1, 1, 4, 4])
%timeit
The slowest run took 42.94 times longer than the fastest. This could mean that an intermediate result is being cached.
100000 loops, best of 3: 3.8 µs per loop
np.unique(ints)
array([1, 2, 3, 4])
#上述程式碼實現功能可以python來實現
%timeit sorted(set(ints))
The slowest run took 25.40 times longer than the fastest. This could mean that an intermediate result is being cached.
1000000 loops, best of 3: 1.75 µs per loop
sorted(set(ints))
[1, 2, 3, 4]
可以看出並不是所有的內建都是效率低的~
np.in1d用於測試一個陣列中的值是否存在於另外一個陣列中,並返回一個大小和測試陣列一樣的布林型陣列
value = np.array([6,0,0,3,2,5])
np.in1d(value,[2,3,6])
array([ True, False, False, True, True, False], dtype=bool)
常見的陣列集合運算
方法 | 說明 |
---|---|
unique(x) | 計算x中的唯一元素,並返回有序結果 |
intersect1d(x,y) | 計算x和y中的公共元素(交集),並返回有序結果 |
union1d(x,y) | 計算x和y的並集,並返回有序結果 |
in1d(x,y) | 得到一個表示“x中元素是否在y陣列中”的布林型陣列 |
setdiff1d(x,y) | 集合的差,即元素在x中且不在y中 |
setxor1d(x,y) | 集合的對稱差(異或),即存在於一個陣列中但不同時存在於兩個陣列中的元素 |
7) 用於陣列的檔案輸入輸出
numpy能夠讀寫磁碟上的文字資料和二進位制資料,pandas中有將表格型資料讀取到記憶體的工具
將陣列以二進位制格式儲存到磁碟
np.save和np.load是讀寫磁碟資料的兩個主要函式,預設情況下,陣列是以未壓縮的原始二進位制格式儲存在副檔名為.npy的檔案中。
arr = np.arange(10)
arr
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
np.save('E:\python\juputer\sameArray',arr)#可以不加字尾,系統會自動加.npy
np.load('E:\python\juputer\sameArray.npy')#必須有字尾
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
此外,還可以將多個陣列儲存到一個壓縮檔案中,將陣列以關鍵字引數的形式傳入即可
array = np.array([1,2,0,0,0,0,0])
np.savez('bb',a=arr,b=array)#貌似只能壓縮到預設路徑下,不知道什麼原因
arch = np.load('bb.npz')
arch['b']
array([1, 2, 0, 0, 0, 0, 0])
存取文字資料
從文字中載入說句是一個非常標準的任務。numpy主要有np.loadtxt()和np.genfromtxt()函式,pandas主要有read_csv和read_table()函式。
arr = np.random.randn(4,3)
arr
array([[-0.51108593, 0.72750055, -0.15797328],
[-0.36643894, 0.55478468, 0.30060344],
[-0.76537983, -0.28501039, -0.14497014],
[ 0.72564297, -1.27952004, 0.30936996]])
np.savetxt('test.txt',arr)
arr = np.loadtxt('test.txt')
arr
array([[-0.51108593, 0.72750055, -0.15797328],
[-0.36643894, 0.55478468, 0.30060344],
[-0.76537983, -0.28501039, -0.14497014],
[ 0.72564297, -1.27952004, 0.30936996]])
8)線性代數
線性代數(如矩陣乘法、矩陣分解、行列式以及其他方陣等)是任何陣列庫的重要組成部分。numpy提供了一個用於矩陣乘法的dot函式(陣列方法),實現陣列的點積。
常用的numpy.linalg函式
函式 | 說明 |
---|---|
diag | 以一維陣列的形式放回方陣的對角線(或非對角線元素),或將一維陣列換為方陣(非對角線元素為0) |
dot | 矩陣乘法 |
trace | 計算對角線元素和 |
det | 計算矩陣的行列式 |
eig | 計算方陣的特徵值和特徵向量 |
inv | 計算方陣的逆 |
pinv | 計算矩陣的Moore-Penrose偽逆 |
qr | 計算qr分解 |
svd | 計算奇異值(SVD) |
solve | 解線性方程組Ax=b,其中A為一個方陣 |
lstsq | 計算Ax=b的最小二乘解 |
x = np.arange(1,12,2).reshape(2,3)
x
array([[ 1, 3, 5],
[ 7, 9, 11]])
y = np.arange(2,13,2).reshape(3,2)
y
array([[ 2, 4],
[ 6, 8],
[10, 12]])
np.dot(x,y)#等價於x.dot(y)
array([[ 70, 88],
[178, 232]])
y
array([[ 2, 4],
[ 6, 8],
[10, 12]])
x = np.random.randn(5,5)
x
array([[ 1.63103816, 0.71983566, 1.10352515, -0.27938298, 0.11040744],
[ 0.41088167, -0.73636959, 1.39466507, 0.02659672, -1.20904744],
[ 0.5186612 , -1.86480014, 2.89604141, -0.63832998, -0.49133989],
[ 1.63042984, 0.57143769, -1.11857589, -0.02013889, 0.46964764],
[ 1.23888832, 3.42855521, -2.36622283, -1.22878746, 1.80597763]])
mat = x.T.dot(x)
np.linalg.inv(mat)
array([[ 0.27742733, -0.19565147, -0.16151662, 0.02161428, -0.04933913],
[-0.19565147, 0.67591051, 0.47450978, 0.64285176, -0.03838762],
[-0.16151662, 0.47450978, 0.6679418 , 1.00350966, 0.69607497],
[ 0.02161428, 0.64285176, 1.00350966, 2.60588578, 1.45256531],
[-0.04933913, -0.03838762, 0.69607497, 1.45256531, 1.87265356]])
mat.T.dot(np.linalg.inv(mat))
array([[ 1.00000000e+00, 1.10290647e-16, 6.50206020e-17,
-9.56263991e-18, 2.31165248e-16],
[ 1.86021783e-16, 1.00000000e+00, -4.42906701e-16,
-2.93319024e-16, -1.88919268e-15],
[ 4.43545563e-17, 1.16736094e-15, 1.00000000e+00,
8.64035632e-16, 4.01786135e-16],
[ -9.10610531e-17, 2.30215482e-16, 2.61428391e-16,
1.00000000e+00, -9.26009142e-17],
[ 2.00085966e-16, -1.58177563e-15, -1.19547067e-15,
-1.29203693e-15, 1.00000000e+00]])
s,v,d = np.linalg.svd(mat)
s
array([[-0.16523474, 0.77808826, 0.58918158, 0.13972992, -0.02483462],
[-0.64883151, 0.20661516, -0.29383095, -0.64803915, 0.17331036],
[ 0.64914815, 0.49923165, -0.41237116, -0.21362089, 0.33718034],
[ 0.10505073, -0.30923038, 0.52695933, -0.24319507, 0.74599661],
[-0.3453783 , 0.08386396, -0.34466264, 0.67508746, 0.54694172]])
v
array([ 37.27592672, 9.26487289, 1.86483196, 0.86523652, 0.23402418])
d
array([[-0.16523474, -0.64883151, 0.64914815, 0.10505073, -0.3453783 ],
[ 0.77808826, 0.20661516, 0.49923165, -0.30923038, 0.08386396],
[ 0.58918158, -0.29383095, -0.41237116, 0.52695933, -0.34466264],
[ 0.13972992, -0.64803915, -0.21362089, -0.24319507, 0.67508746],
[-0.02483462, 0.17331036, 0.33718034, 0.74599661, 0.54694172]])
9)隨機數生成
numpy.random模組是對python內建random進行補充,增加了一些用於高效生成多種概率分佈的樣本值的函式,例如,你可以用normal來得到一個標準正態分佈的4*4樣本陣列。
常用的隨機數生成函式
函式 | 說明 |
---|---|
seed | 確定隨機數生成器的種子 |
permutation | 返回一個序列的隨機排列或返回一個隨機排列的範圍 |
shuffle | 對一個序列就地隨機排列 |
rand | 產生均勻分佈的樣本值 |
randint | 從給定的上下限範圍內隨機選取整數 |
randn | 產生正態分佈(平均數為0,標準差為1)的樣本值,類似於MATLAB介面 |
binomial | 產生二項分佈的樣本值 |
normal | 產生正態分佈(高斯分佈)的樣本值 |
beta | 產生beta分佈的樣本值 |
chisquare | 產生卡方分佈的樣本值 |
gamma | 產生gamma分佈的樣本值 |
uniform | 產生[0,1)均勻分佈的樣本值 |
#產生高斯分佈
sample = np.random.normal(size=(4,4))
sample
array([[ 0.89509853, -0.83225074, 1.29474565, 0.45655647],
[-1.43400126, 1.32985572, 2.30055355, 2.46808663],
[-2.4563378 , -0.66266506, -1.15600003, -0.60034993],
[-1.79678809, -0.69896066, 1.02434411, 0.1271823 ]])
總結
1)條件邏輯表示式不改變原陣列,會返回新的布林型陣列
2)聚合函式不改變原陣列,返回結果值
3)監測和檢驗函式不改變原陣列,返回布林型資料
4)排序函式能夠改變原陣列,在原來的資料上修改
5)唯一化及集合邏輯不改變原陣列,返回新的陣列
6)線性代數、矩陣運算不改變原陣列,返回結果陣列
7)切片相當於引用,指向同一記憶體區,因此不管改變原陣列,還是新的引用變數都會改變原陣列
8) numpy元素級通用函式不改變原陣列
相關文章
- NumPy 陣列排序、過濾與隨機數生成詳解陣列排序隨機
- Python科學計算之Numpy陣列生成與運算Python陣列
- numpy——陣列的計算陣列
- NumPy 基礎 (二) - 陣列運算陣列
- JavaScript陣列隨機排序JavaScript陣列隨機排序
- python numpy基礎 陣列和向量計算Python陣列
- [隨機數詳解]生成一個隨機數,生成指定範圍的隨機數及隨機陣列去重隨機陣列
- python-資料分析-Numpy-3、陣列的運算Python陣列
- python怎麼生成隨機不重複陣列Python隨機陣列
- numpy各種生成隨機數的方法隨機
- 教你如何運用golang 實現陣列的隨機排序Golang陣列隨機排序
- python生成隨機數、隨機字串Python隨機字串
- python 隨機數生成Python隨機
- Numpy中的矩陣運算矩陣
- JavaScript 陣列中元素隨機打亂排序JavaScript陣列隨機排序
- JS陣列隨機排序的三種方法JS陣列隨機排序
- 【numpy學習筆記】陣列的建立和基本運算筆記陣列
- Python列表建立NumPy陣列Python陣列
- NumPy 通用函式(ufunc):高效能陣列運算的利器函式陣列
- 生成隨機字串並排序隨機字串排序
- 隨機字串生成與排序隨機字串排序
- Python生成隨機數random模組Python隨機random
- Python中如何生成隨機數?Python隨機
- python生成隨機數的方法Python隨機
- Python隨機數生成方法Python隨機
- Python科學計算庫Numpy陣列的初始化和基本操作Python陣列
- 計算機系統002 – 數值運算計算機
- 計算機系統002 - 數值運算計算機
- NumPy快餐教程(1) – 如何生成多維陣列陣列
- python資料分析之Numpy資料庫第三期陣列的運算Python資料庫陣列
- 生成隨機數隨機
- 陣列(2)陣列運算及典例(求解素數的方法)陣列
- 怎麼用Python生成隨機數Python隨機
- Python Numpy的陣列array和矩陣matrixPython陣列矩陣
- python之Numpy 排序搜尋計數及集合操作Python排序
- 實現陣列的隨機排序(含洗牌演算法)陣列隨機排序演算法
- js可以使用 Math(算數) 物件生成隨機數JS物件隨機
- random隨機生成10個數,然後氣泡排序random隨機排序