Python 机器学习的利器(3)
K 邻近算法(KNN)
可以将房源想象为实例,将房源的位置和价格将房源分类为推荐房源和非推荐房源。
最近苹果贵了,我们都会去水果超市买一些应季的水果,同一类水果如苹果,会根据其品种、产地以及大小而价格不等。
所以可以根据苹果直径定义一个区间来表示一个价格等级,这个和今天讨论如何通过花瓣和鄂的尺寸进行区分种类有点相似。
可以通过训练数据计算出用于分类的模板(尺寸一定范围)。
k近邻算法简称kNN算法,是由Thomas等人在1967年提出。
核心内容就是:要确定一个样本的类别,可以计算它与所有训练样本的距离,然后找出和该样本最接近的k个样本,统计这些样本的类别进行投票,票数最多的那个类就是分类结果。因为直接比较样本和训练样本的距离,kNN算法也被称为基于实例的算法。
有关如何实现 k 最邻近算法的一般步骤
- 列出所有已知类别的实例作为参照
然后对于要推测类别的实例周围离他最近的一些实例类别属于哪一类,然后根据邻近实例类别来推测他类别 - 选择 k 参数,也就是选择要推测实例的周围用于推测他类别的实例的数量,通常 k 值不会太大,k 值具体取值也是我们优化的对象
- 计算要推测实例与所有已知实例的距离
- 选择 K 个最近的距离
- 最后根据选取实例的具体类别,根据少数服从多数的法则进行投票
有关算法中关键知识点
如何计算未知实例与已知实例距离呢,其实很简单就是计算距离,同样适用于多维计算距离。
当然计算距离除了此方法还有余弦值、相关度和曼哈顿距离
import math
def cal_euclidean_distance(x1, y1, x2, y2):
d = math.sqrt(math.pow((x1 - x2),2) + math.pow((y1 - y2),2))
return d
l = []
l.append({x:3,y:104})
l.append({x:2,y:100})
l.append({x:1,y:81})
l.append({x:101,y:10})
l.append({x:99,y:5})
l.append({x:98,y:2})
pred_p = {x:18,y:90}
dist_l = []
for p in l:
dist = cal_euclidean_distance(p[x],p[y],pred_p[x],pred_p[y])
dist_l.append(dist)
for d in dist_l:
print(d)
pred_p 是我们未知点,通过计算未知点为其他点计算距离
20.5182845287
18.8679622641
19.2353840617
115.277925033
117.413798167
118.928549979
算法的优点和缺点
所谓增大 K 值其实我们是不断扩大其(未知值)搜索半径来获取更多已知实例,KNN 算法是 K 选择很敏感。
优点就是简单直观
缺点需要大量空间存储所有数据,需要计算未知点与已知点间距离,所有对于大量数据会有局限性、
在 scikit-learn 中提供我们学习会用到机器学习模型的实现,k 近邻分类算法可以在 neighbors 模块找到,是 KNeighborsClassifier 所提供的,我们要做的只是实例化一个 KNeighborsClassifier 实例,便可以使用来基于 k 邻近算法来构建模型。
from sklearn.neighbors import KNeighborsClassifier
knn = KNeighborsClassifier(n_neighbors=1)
knn.fit(X_train,y_train)
可以调用 knn 的 fit 方法来创建模型,我们需要提供训练模型数据,X_train 为特征值,y_train 为该特征值对应类别
import numpy as np
X_new = np.array([[5,2.9,1,0.2]])
prediction = knn.predict(X_new)
print("Prediction:{}".format(prediction))
print("Predicted target name: {}".format(iris_dataset['target_names'][prediction]))