|
| 1 | +# _*_coding:utf-8-*_ |
| 2 | +import numpy as np |
| 3 | +# 定义矩阵变量并输出变量的一些属性 |
| 4 | +# 用np.array()生成矩阵 |
| 5 | +arr=np.array([[1,2,3], |
| 6 | + [4,5,6]]) |
| 7 | + |
| 8 | +print(arr) |
| 9 | +print('number of arr dimensions: ',arr.ndim) |
| 10 | +print('~ ~ ~ shape: ',arr.shape) |
| 11 | +print('~ ~ ~ size: ', arr.size) |
| 12 | + |
| 13 | +# 输出结果: |
| 14 | +[[1 2 3] |
| 15 | + [4 5 6]] |
| 16 | +number of arr dimensions: 2 |
| 17 | +~ ~ ~ shape: (2, 3) |
| 18 | +~ ~ ~ size: 6 |
| 19 | + |
| 20 | +# 定义一些特殊矩阵 |
| 21 | +# 指定矩阵数据类型 |
| 22 | +arr=np.array([[1,2,3], |
| 23 | + [4,5,6]], |
| 24 | + dtype=np.float64) # 我的电脑np.int是int32,还可以使用np.int32/np.int64/np.float32/np.float64 |
| 25 | +print(arr.dtype) |
| 26 | + |
| 27 | +# 用np.zeros()生成全零矩阵 |
| 28 | +arr_zeros=np.zeros( (2,3) ) |
| 29 | +print(arr_zeros) |
| 30 | + |
| 31 | +# 用np.ones()生成全一矩阵 |
| 32 | +arr_ones=np.ones( (2,3) ) |
| 33 | +print(arr_ones) |
| 34 | + |
| 35 | +# 生成随机矩阵np.random.random() |
| 36 | +arr_random=np.random.random((2,3)) |
| 37 | +print(arr_random) |
| 38 | + |
| 39 | +# 用np.arange()生成数列 |
| 40 | +arr=np.arange(6,12) |
| 41 | +print(arr) |
| 42 | + |
| 43 | +# 用np.arange().reshape()将数列转成矩阵 |
| 44 | +arr=np.arange(6,12).reshape( (2,3) ) |
| 45 | +print(arr) |
| 46 | + |
| 47 | +# 用np.linspace(开始,结束,多少点划分线段),同样也可以用reshape() |
| 48 | +arr=np.linspace(1,5,3) |
| 49 | +print(arr) |
| 50 | + |
| 51 | +# 矩阵运算 |
| 52 | +arr1=np.array([1,2,3,6]) |
| 53 | +arr2=np.arange(4) |
| 54 | + |
| 55 | +# 矩阵减法,加法同理 |
| 56 | +arr_sub=arr1-arr2 |
| 57 | +print(arr1) |
| 58 | +print(arr2) |
| 59 | +print(arr_sub) |
| 60 | + |
| 61 | +# 矩阵乘法 |
| 62 | +arr_multi=arr1**3 # 求每个元素的立方,在python中幂运算用**来表示 |
| 63 | +print(arr_multi) |
| 64 | + |
| 65 | +arr_multi=arr1*arr2 # 元素逐个相乘 |
| 66 | +print(arr_multi) |
| 67 | + |
| 68 | +arr_multi=np.dot(arr1, arr2.reshape((4,1))) # 维度1*4和4*1矩阵相乘 |
| 69 | +print(arr_multi) |
| 70 | + |
| 71 | +arr_multi=np.dot(arr1.reshape((4,1)), arr2.reshape((1,4))) # 维度4*1和1*4矩阵相乘 |
| 72 | +print(arr_multi) |
| 73 | + |
| 74 | +arr_multi=arr1.dot(arr2.reshape((4,1))) # 也可以使用矩阵名.doc(矩阵名) |
| 75 | +print(arr_multi) |
| 76 | + |
| 77 | +# 三角运算:np.sin()/np.cos()/np.tan() |
| 78 | +arr_sin=np.sin(arr1) |
| 79 | +print(arr_sin) |
| 80 | + |
| 81 | +# 逻辑运算 |
| 82 | +print(arr1<3) # 查看arr1矩阵中哪些元素小于3,返回[ True True False False] |
| 83 | + |
| 84 | +# 矩阵求和,求矩阵最大最小值 |
| 85 | +arr1=np.array([[1,2,3], |
| 86 | + [4,5,6]]) |
| 87 | +print(arr1) |
| 88 | +print(np.sum(arr1)) # 矩阵求和 |
| 89 | +print(np.sum(arr1,axis=0)) # 矩阵每列求和 |
| 90 | +print(np.sum(arr1,axis=1).reshape(2,1)) # 矩阵每行求和 |
| 91 | + |
| 92 | +print(np.min(arr1)) # 求矩阵最小值 |
| 93 | +print(np.min(arr1,axis=0)) |
| 94 | +print(np.min(arr1,axis=1)) |
| 95 | + |
| 96 | +print(np.max(arr1)) # 求矩阵最大值 |
| 97 | + |
| 98 | +print(np.mean(arr1)) # 输出矩阵平均值,也可以用arr1.mean() |
| 99 | +print(np.median(arr1)) # 输出矩阵中位数 |
| 100 | + |
| 101 | +# 输出矩阵某些值的位置 |
| 102 | +arr1=np.arange(2,14).reshape((3,4)) |
| 103 | +print(arr1) |
| 104 | + |
| 105 | +print(np.argmin(arr1)) # 输出矩阵最小值的位置,0 |
| 106 | +print(np.argmax(arr1)) # 输出矩阵最大值的位置,11 |
| 107 | + |
| 108 | +print(np.cumsum(arr1)) # 输出前一个数的和,前两个数的和,等等 |
| 109 | +print(np.diff(arr1)) # 输出相邻两个数的差值 |
| 110 | + |
| 111 | +arr_zeros=np.zeros((3,4)) |
| 112 | +print(np.nonzero(arr_zeros)) #输出矩阵非零元素位置,返回多个行向量,第i个行向量表示第i个维度 |
| 113 | +print(np.nonzero(arr1)) |
| 114 | + |
| 115 | +print(np.sort(arr1)) # 矩阵逐行排序 |
| 116 | +print(np.transpose(arr1)) # 矩阵转置,也可以用arr1.T |
| 117 | + |
| 118 | +print(np.clip(arr1,5,9)) #将矩阵中小于5的数置5,大于9的数置9 |
| 119 | + |
| 120 | +# numpy索引 |
| 121 | +arr1=np.array([1,2,3,6]) |
| 122 | +arr2=np.arange(2,8).reshape(2,3) |
| 123 | + |
| 124 | +print(arr1) |
| 125 | +print(arr1[0]) # 索引从0开始计数 |
| 126 | + |
| 127 | +print(arr2) |
| 128 | +print(arr2[0][2]) # arr[行][列],也可以用arr[行,列] |
| 129 | +print(arr2[0,:]) # 用:来代表所有元素的意思 |
| 130 | +print(arr2[0,0:3]) # 表示输出第0行,从第0列到第2列所有元素 |
| 131 | + # 注意python索引一般是左闭右开 |
| 132 | + |
| 133 | +# 通过for循环每次输出矩阵的一行 |
| 134 | +for row in arr2: |
| 135 | + print(row) |
| 136 | + |
| 137 | +# 如果要每次输出矩阵的一列,就先将矩阵转置 |
| 138 | +arr2_T=arr2.T |
| 139 | +print(arr2_T) |
| 140 | +for row in arr2_T: |
| 141 | + print(row) |
| 142 | + |
| 143 | +# 将矩阵压成一行逐个输出元素 |
| 144 | +arr2_flat=arr2.flatten() |
| 145 | +print(arr2_flat) |
| 146 | + |
| 147 | +for i in arr2.flat: # 也可以用arr2.flatten() |
| 148 | + print(i) |
| 149 | + |
| 150 | +# 矩阵合并与分割 |
| 151 | +# 矩阵合并 |
| 152 | +arr1=np.array([1,2,3,6]) |
| 153 | +arr2=np.arange(4) |
| 154 | +arr3=np.arange(2,16+1,2).reshape(2,4) |
| 155 | +print(arr1) |
| 156 | +print(arr2) |
| 157 | +print(arr3) |
| 158 | + |
| 159 | +arr_hor=np.hstack((arr1,arr2)) # 水平合并,horizontal |
| 160 | +arr_ver=np.vstack((arr1,arr3)) # 垂直合并,vertical |
| 161 | +print(arr_hor) |
| 162 | +print(arr_ver) |
| 163 | + |
| 164 | +# 矩阵分割 |
| 165 | +print('arr3: ',arr3) |
| 166 | +print(np.split(arr3,4,axis=1)) # 将矩阵按列均分成4块 |
| 167 | +print(np.split(arr3,2,axis=0)) # 将矩阵按行均分成2块 |
| 168 | +print(np.hsplit(arr3,4)) # 将矩阵按列均分成4块 |
| 169 | +print(np.vsplit(arr3,2)) # 将矩阵按行均分成2块 |
| 170 | +print(np.array_split(arr3,3,axis=1)) # 将矩阵进行不均等划分 |
| 171 | + |
| 172 | +# numpy复制:浅复制,深复制 |
| 173 | +# 浅复制 |
| 174 | +arr1=np.array([3,1,2,3]) |
| 175 | +print(arr1) |
| 176 | +a1=arr1 |
| 177 | +b1=a1 |
| 178 | +# 通过上述赋值运算,arr1,a1,b1都指向了同一个地址(浅复制) |
| 179 | +print(a1 is arr1) |
| 180 | +print(b1 is arr1) |
| 181 | +print(id(a1)) |
| 182 | +print(id(b1)) |
| 183 | +print(id(arr1)) |
| 184 | + |
| 185 | +# 会发现通过b1[0]改变内容,arr1,a1,b1的内容都改变了 |
| 186 | +b1[0]=6 |
| 187 | +print(b1) |
| 188 | +print(a1) |
| 189 | +print(arr1) |
| 190 | + |
| 191 | +# 深复制 |
| 192 | +arr2=np.array([3,1,2,3]) |
| 193 | +print('\n') |
| 194 | +print(arr2) |
| 195 | +b2=arr2.copy() # 深复制,此时b2拥有不同于arr2的空间 |
| 196 | +a2=b2.copy() |
| 197 | +# 通过上述赋值运算,arr1,a1,b1都指向了不同的地址(深复制) |
| 198 | +print(id(arr2)) |
| 199 | +print(id(a2)) |
| 200 | +print(id(b2)) |
| 201 | +# 此时改变b2,a2的值,互不影响 |
| 202 | +b2[0]=1 |
| 203 | +a2[0]=2 |
| 204 | +print(b2) |
| 205 | +print(a2) |
| 206 | +print(arr2) |
| 207 | + |
| 208 | +# 线性代数模块(linalg) |
| 209 | +# 求范数 |
| 210 | +a=np.array([5,12]) |
| 211 | +print(a) |
| 212 | +b=np.linalg.norm(a) # norm表示范数,默认求2范数,ord=1求1范数,ord=np.inf求无穷范数 |
| 213 | +print(b) |
| 214 | + |
| 215 | +# 求矩阵的迹、行列式、秩、特征值、特征向量 |
| 216 | +b = np.array([ |
| 217 | + [1, 2, 3], |
| 218 | + [4, 5, 6], |
| 219 | + [7, 8, 9] |
| 220 | +]) |
| 221 | + |
| 222 | +print(np.trace(b)) # 15,求矩阵的迹(主对角线上各个元素的总和) |
| 223 | + |
| 224 | +c=np.linalg.det(b) |
| 225 | +print(c) # 输出一个很小的值6.66133814775e-16,求矩阵的行列式值 |
| 226 | + # 如果希望输出为0,使用round(c, 2),四舍五入保留小数点后两位 |
| 227 | + # 不过对精度要求高可以使用decimal模块 |
| 228 | + |
| 229 | +c=np.linalg.matrix_rank(b) |
| 230 | +print(c) # 2,求矩阵的秩 |
| 231 | + |
| 232 | +u,v=np.linalg.eig(b) # u为特征值 |
| 233 | +print(u) |
| 234 | +print(v) |
| 235 | + |
| 236 | +# 矩阵分解 |
| 237 | +# Cholesky分解并重建 |
| 238 | +d = np.array([ |
| 239 | + [2, 1], |
| 240 | + [1, 2] |
| 241 | +]) |
| 242 | + |
| 243 | +l = np.linalg.cholesky(d) |
| 244 | +print(l) # 得到下三角矩阵 |
| 245 | +e=np.dot(l, l.T) |
| 246 | +print(e) # 重建得到矩阵d |
| 247 | + |
| 248 | + |
| 249 | +# 对不正定矩阵,进行SVD分解并重建 |
| 250 | +U, s, V = np.linalg.svd(d) |
| 251 | + |
| 252 | +S = np.array([ |
| 253 | + [s[0], 0], |
| 254 | + [0, s[1]] |
| 255 | +]) |
| 256 | + |
| 257 | +print(np.dot(U, np.dot(S, V))) # 重建得到矩阵d |
| 258 | + |
| 259 | +# 矩阵乘法 |
| 260 | +# https://docs.scipy.org/doc/numpy/reference/generated/numpy.dot.html#numpy.dot |
| 261 | +print(np.dot(3, 4)) # 12,0-D矩阵相乘(也就是标量相乘) |
| 262 | + |
| 263 | +print(np.dot([2j, 3j], [2j, 3j])) # (-13+0j),1-D矩阵相乘(实际上是向量做点积) |
| 264 | + |
| 265 | +a=[[1, 0], [0, 1]] |
| 266 | +b=[[4, 1, 0], [2, 2, 0]] |
| 267 | +print(np.dot(a, b)) |
| 268 | +''' |
| 269 | +array([[4, 1], |
| 270 | + [2, 2]]) |
| 271 | +2-D矩阵相乘 |
| 272 | +这里是2*2矩阵和2*3矩阵相乘,结果为2*3矩阵 |
| 273 | +''' |
| 274 | + |
| 275 | +a=[[1, 0], [1, 2]] |
| 276 | +b=[2,2] |
| 277 | +c=np.dot(a,b) |
| 278 | +print(c) |
| 279 | +''' |
| 280 | +[2 6] |
| 281 | +注意这里b是向量 |
| 282 | +numpy处理时并不是按照矩阵乘法规则计算 |
| 283 | +而是向量点积 |
| 284 | +也就是np.dot([1, 0],[1, 2])和np.dot([1, 2],[2,2]) |
| 285 | +''' |
| 286 | + |
| 287 | +# 再做个实验来区别向量乘法和矩阵乘法 |
| 288 | +b=np.array([ |
| 289 | + [1, 2, 3], |
| 290 | + [4, 5, 6], |
| 291 | + [7, 8, 9] |
| 292 | +]) |
| 293 | + |
| 294 | +# 这里插播一下,np.array([1,0,1])是3维向量,而不是1*3的矩阵 |
| 295 | +c1=np.array([[1,0,2]]) |
| 296 | +print(c1.shape) # (1, 3),这是一个1*3的矩阵 |
| 297 | +c2=np.array([1,0,2]) |
| 298 | +print(c2.shape) # (3,),这是一个3维向量 |
| 299 | + |
| 300 | +# print(np.dot(b,c1)) # 报错,不符合矩阵乘法规则 |
| 301 | +print(np.dot(b,c2)) # [ 7 16 25],点积运算 |
| 302 | + |
| 303 | +print(np.dot(c1,b)) # [[15 18 21]],矩阵乘法运算规则 |
| 304 | +print(np.dot(c2,b)) # [15 18 21],点积运算 |
| 305 | + |
| 306 | +# 还要补充一下,如果是用python自带的*运算符计算则是广播机制 |
| 307 | +print(b*c1) # print(b*c2)结果一样 |
| 308 | +''' |
| 309 | +[[ 1 0 6] |
| 310 | + [ 4 0 12] |
| 311 | + [ 7 0 18]] |
| 312 | +''' |
| 313 | +print(b+c1) # print(b*c2)结果一样 |
| 314 | +''' |
| 315 | +[[ 2 2 5] |
| 316 | + [ 5 5 8] |
| 317 | + [ 8 8 11]] |
| 318 | +''' |
0 commit comments