KNN - 打斗接吻次数划分电影类型
1.K-近邻法的工作原理
K-近邻法(K-Nearest Neighbor),它的本质是通过距离判断两个样本是否相似,如果距离够近就认为它们足够相似属于同一类别。
“近朱者赤,近墨者黑”,“少数服从多数,一点算一票”,“越相近越相似”,这些也是KNN的基本假设。
实现过程如下:
- 计算待分类物体与其他物体之间的距离。
- 统计距离最近的K个邻居。
- 对于K个最近的邻居,它们属于哪个分类最多,待分类物体就属于哪一类。
2.优缺点
优点:
- 对数据类型没有要求;
- 与异常值不敏感;
缺点:
- 不合适解决样本不平衡的问题。(比如有些分类的样本非常少,那么该类别的分类准确率就会低很多)
3.应用场景
K近邻算法完全跟着数据走的,没有高深的数学模型,适用于需要解释一个特别容易理解的模型的场景,比如向用户解释最简单的推荐算法。
案例:根据打斗和接吻次数来划分电影类型
#!/usr/bin/env python
# coding: utf-8
from sklearn.neighbors import KNeighborsClassifier
from sklearn.preprocessing import MinMaxScaler
import pandas as pd
# 数据准备
data = [["California Man", 3, 104, "爱情片"],
["He's Not Really into Dudes", 2, 100, "爱情片"],
["Beautiful Woman", 1, 81, "爱情片"],
["Kevin Longblade", 101, 10, "动作片"],
["Robo Slayer 3000", 99, 5, "动作片"],
["Amped II", 98, 2, "动作片"]]
columns = ["电影名称", "打斗次数", "接吻次数", "电影类型划分"]
df = pd.DataFrame(data=data, columns=columns)
train_x = df.loc[:,["打斗次数", "接吻次数"]]
train_y = df.loc[:,["电影类型划分"]]
print(train_x, "\n","-" * 20,"\n", train_y)
"""
打斗次数 接吻次数
0 3 104
1 2 100
2 1 81
3 101 10
4 99 5
5 98 2
--------------------
电影类型划分
0 爱情片
1 爱情片
2 爱情片
3 动作片
4 动作片
5 动作片
"""
# 数据规范[0,1]
min_max_scaler = MinMaxScaler()
train_x_minmax = min_max_scaler.fit_transform(train_x)
print(train_x_minmax)
"""
array([[0.02 , 1. ],
[0.01 , 0.96078431],
[0. , 0.7745098 ],
[1. , 0.07843137],
[0.98 , 0.02941176],
[0.97 , 0. ]])
"""
# 创建KNN分类器
knn = KNeighborsClassifier()
# 分类器训练
knn.fit(train_x_minmax, train_y)
# 用训练好的分类器预测,已知有一部未知电影A的打斗和接吻次数是18和90次
knn.predict([[18,90]])
# 使用KNN分类输出结果如下
"""
array(['爱情片'], dtype=object)
"""
4.延伸提问
1.计算距离的几种方法?
- 欧氏距离,用于各种空间的距离计算问题;
- 曼哈顿距离,受到维度的限制,常用于计算水平或者垂直的距离;
- 闵可夫斯基距离;
- 切比雪夫距离;
- 余弦距离,常用于衡量用户对内容兴趣的区分度,有基于用户的协同推荐,还有基于商品的协同推荐。
2.K-近邻算法常常采用什么方式进行分类?它的优势在哪?
- 采用KD树(K-Dimensional 的缩写),KD树是对数据点在K维空间中划分的一种数据结构,它是二叉树数据结构。
- 采用二叉树的增删改查操作,就大大提升了KNN的搜索效率。
2.样本不平衡会给KNN造成什么影响?如何缓解?
- 可能造成大数量的样本占多数,但是这类样本不接近目标样本。而数量小的这类样本很靠近目标样本。KNN只关心哪类样本的数量最多,而不去把距离远近考虑在内。可以考虑用权重进行改进,距离实例较近的点赋予较高的权重,较远的点赋予较低的权重。
3.KNN不仅可以做分类,还可以做回归,举例讲讲?
- 先说分类,在前面案例中,如果想要对未知电影进行类型划分,这是一个分类问题。(具体来说,有一部未知电影A,知道它的打斗次数x,接吻次数y,把它放在二维的坐标轴上,A的坐标是(x,y),然后计算电影A最近的都有哪些电影,这些电影中的大多数属于哪个分类,那么电影A就属于哪个分类)。
- 回归,还是以电影为例说明,如果有一部电影X,想要预测它的某个属性值,比如打斗次数,就会先计算待测点(新电影X)到已知点的距离,选择距离最近的K个点对应的平均值。(K部电影的打斗次数的平均值)
4.KNN中的K值如何选择?过大或过小会造成什么影响?
- K值太小,容易过拟合
- K值太大,容易欠拟合
- 选取K值采用交叉验证的方式
相关参考:
https://www.nowcoder.com/tutorial/10080/9a06bdda45f24ac0991bd8b5ad9ba22e
https://time.geekbang.org/column/article/80983