基於最鄰近演算法的分類,本質上是對離散的資料標籤進行預測,實際上,最鄰近演算法也可以用於對連續的資料標籤進行預測,這種方法叫做基於最鄰近資料的迴歸,預測的值(即資料的標籤)是連續值,通過計算資料點最臨近資料點平均值而獲得預測值。
一,sklearn的knn迴歸
scikit-learn實現了兩個不同的最鄰近迴歸模型:
- KNeighborsRegressor:根據每個查詢點的最鄰近的k個資料點的均值作為預測值,其中,k是使用者指定的整數。
- RadiusNeighborsRegressor:基於查詢點的固定半徑內的資料點的均值作為預測值,其中r是使用者指定的浮點值。
迴歸模擬器的定義如下,該定義只列出最重要的引數,詳細引數請參考sicikit-learn 官網:
sklearn.neighbors.KNeighborsRegressor(n_neighbors=5, weights='uniform', algorithm='auto', metric='minkowski',...) sklearn.neighbors.RadiusNeighborsRegressor(radius=1.0, weights='uniform', algorithm='auto', metric='minkowski',...)
引數註釋:
- radius:尋找最鄰近資料點的半徑
- n_neighbors:最鄰近的鄰居數量
- algorithm:尋找最鄰近的資料點的演算法,有效值是['auto','ball_tree','kd_tree','brute']
- metric:計算距離的度量,詳細資訊請檢視:
DistanceMetric
- weights:權重,預設值weights ='uniform',為每個鄰居分配統一的權重。 weights ='distance'分配的權重與距查詢點的距離成反比。用於也可以提供定義函式來計算權重。在某些情況下,最好對鄰居加權,以使較近的鄰居對擬合的貢獻更大,這可以通過weights關鍵字完成。
最基本的最鄰近迴歸使用統一的權重,也就是說,在特定範圍中的每個資料點對查詢點的分類(迴歸)的作用是相同的。在某些情況下,對權重點進行加權可能會比較有利,以使鄰近的點比遠離的點對迴歸的貢獻更大,這可以通過weights關鍵字完成。預設值weights ='uniform',為所有點分配相等的權重。 weights ='distance'分配的權重與距查詢點的距離成反比。
二,基於最鄰近的資料點的數量來預測
當使用knn計算某個資料點的預測值時,模型會從訓練資料集中選擇離該資料點最近的k個資料點,並且把它們的y值取均值,把該均值作為新資料點的預測值:
from sklearn.neighbors import KNeighborsRegressor
對於knn分類,使用score方法評估模型,對於迴歸的問題,返回的是R^2分數,R^2分數也叫做決定係數,是迴歸模型預測的優度度量,位於0到1之間,R^2等於1對應完美預測,R^2等於0對應於常數模型,即總是預測訓練集響應(y_train)的均值。
from sklearn.datasets import make_regression from sklearn.neighbors import KNeighborsRegressor from sklearn.model_selection import train_test_split kng=KNeighborsRegressor(n_neighbors=5) x_data,y_data=make_regression(n_features=1,n_informative=1,noise=50,random_state=1) x_train,x_test,y_train,y_test=train_test_split(x_data,y_data,random_state=1) kng.fit(x_train,y_train) prediction=kng.predict(x_test) kng_test_score=kng.score(x_test,y_test) kng_train_score=kng.score(x_train,y_train)
print('test data score:{:.2f}'.format(kng_test_score))
三,knn迴歸模型的優缺點
knn迴歸有兩個重要的引數:最鄰近資料點的數量k,資料點之間距離的度量方法。
在實踐中,通常使用較小的k值,在knn分類中通常把k值設定為奇數,便於找到多數鄰居的標籤。預設的距離度量是歐式距離,它在多數情況下的效果都很好,除此之外,還有曼哈頓距離等,詳細資訊,請閱讀《Scipy 學習第3篇:數字向量的距離計算》。
在確定knn迴歸或knn分類的k值時,可以通過摺疊交叉驗證來尋找最佳的k值,示例程式碼如下:
from sklearn import datasets from sklearn.neighbors import KNeighborsClassifier from sklearn.model_selection import GridSearchCV #通過網路方式來獲取引數 # 匯入iris資料集 iris2=datasets.load_iris() X2=iris2.data y2=iris2.target print(X2.shape,y2.shape) # 設定需要搜尋的K值,'n_neightbors'是sklearn中KNN的引數 parameters={'n_neightbors':[1,3,5,7,9,11,13,15]} knn=KNeighborsClassifier()#注意:這裡不用指定引數 # 通過GridSearchCV來搜尋最好的K值。這個模組的內部其實就是對每一個K值進行評估 clf=GridSearchCV(knn,parameters,cv=5) #5折 clf.fit(X2,y2) # 輸出最好的引數以及對應的準確率 print("最終最佳準確率:%.2f"%clf.best_score_,"最終的最佳K值",clf.best_params_)
knn迴歸模型的優點之一是模型很容易理解,通常不需要過多的調參就可以得到不錯的效能,並且構建模型的速度通常很快。但是使用knn演算法時,對資料進行預處理是很重要的,對特徵很多的資料集、對於大多數特徵值都為0的資料集,效果往往不是很好。
雖然k鄰近演算法很容易理解,但是由於預測速度慢,且不能處理具有很多特徵的資料集,所以,在實踐中往往不會用到。
參考文件:
sklearn.neighbors.KNeighborsRegressor