文章目錄
操作平臺: windows10, python37, jupyter
數據下載: https://www.lanzous.com/iae2wyh
1、讀取數據
- 這些數據全部都是圖片,從0~9,一個數字共500張,並且每個數字圖片都在對應的文件夾下,以
自身值_序號.bmp
的方式進行命名,如圖:
● data文件夾下:
● 0文件夾下:
1.1、導入相關庫
import numpy as np
from sklearn.neighbors import KNeighborsClassifier
import matplotlib.pyplot as plt
%matplotlib inline
1.2、讀取一張圖片測試
img = plt.imread('./data/0/0_1.bmp')
plt.imshow(img,cmap = plt.cm.gray) #這些圖片都是黑白的,
1.3、讀取所有圖片
data = []
for i in range(10):
for j in range(1,501):
data.append(plt.imread('./data/%d/%d_%d.bmp'%(i,i,j)))
查看data大小:
len(data)
5000
2、數據預處理
2.1、list轉numpy
- 上面得到的data是list類型,但是圖片是用維度的,需要把它的數據還原。
# 數據
X = np.array(data)
X.shape
(5000, 28, 28)
2.2、添加對應數字
- 上面得到的信息只是圖片本身的數據,但是卻不明確是哪個數字,所以必須給它指定,並賦值給 y。
(1)構造數組
y = [0,1,2,3,4,5,6,7,8,9]*500
y
結果:從0-9,0-9,0-9,一共500次。總共有5000個數值。
(2)數組轉numpy
y = np.array(y)
y
array([0, 1, 2, ..., 7, 8, 9])
(3)排序
- 因爲上面的data是每一個文件夾分別讀取的,一樣的數值就在一起了,前500個全是0, 第二個500全是1… …,我們只需要y排序就可以對應它的值了。
y.sort()
y
array([0, 0, 0, ..., 9, 9, 9])
3、隨機抽取訓練集與測試集
- 隨機抽樣,不影響算法,算法根據距離來進行
- 訓練集和測試集可能會被重複抽取到
index = np.random.randint(0,5000,size = 4000)#隨機抽取80%來訓練
X_train = X[index]
y_train = y[index]
index = np.random.randint(0,5000,size = 1000) #隨機抽取20%來測試
X_test = X[index]
y_test = y[index]
(1)查看數據形狀
結果分析: x的訓練集和y的訓練集數據維度不能對應,x是3維的,y屬於1維的,必須要把它統一維度才能進行運算,接下了對x進行降維處理。
(2)降維處理
- 每張圖片的分辨率都是28*28,相乘等於784
X_train.reshape(4000,784)
array([[255, 255, 255, ..., 255, 255, 255],
[255, 255, 255, ..., 255, 255, 255],
[255, 255, 255, ..., 255, 255, 255],
...,
[255, 255, 255, ..., 255, 255, 255],
[255, 255, 255, ..., 255, 255, 255],
[255, 255, 255, ..., 255, 255, 255]], dtype=uint8)
4、訓練模型並預測
4.1、訓練模型
%%time
knn = KNeighborsClassifier(n_neighbors=5)#鄰近值個數爲5
knn.fit(X_train.reshape(4000,-1),y_train) #如果不想計算出28*28=784,可以直接用-1代替784
Wall time: 1.97 s
KNeighborsClassifier(algorithm='auto', leaf_size=30, metric='minkowski',
metric_params=None, n_jobs=None, n_neighbors=5, p=2,
weights='uniform')
4.2、預測
%%time #耗時Wall time: 12.1 s
# 預測
y_ = knn.predict(X_test.reshape(1000,784))
查看前20個結果:
4.3、計算準確率
(1)方法一
(y_test == y_).mean()
0.931
(2)方法二
knn.score(X_test.reshape(1000,-1),y_test)
0.931
4.4、精確度調整
%%time
# n_neighbors=鄰近值,weights=權重, p = 距離,n_jobs=線程
knn = KNeighborsClassifier(n_neighbors=5,weights='distance', p = 1,n_jobs=-1)
knn.fit(X_train.reshape(4000,-1),y_train) #訓練模型
# predict ,計算準確率
knn.score(X_test.reshape(1000,-1),y_test)
Wall time: 3.88 s
0.953
5、識別某張圖片
5.1、讀取圖片
img = plt.imread('./data/9/9_1.bmp') #隨便讀取一張圖片
plt.imshow(img,cmap = plt.cm.gray) #展示
plt.show()
5.2、識別數字
knn.predict(img.reshape(1,-1))[0]
9