一、介绍

你好,我是悦创。

博客首发:https://bornforthis.cn/column/Machine-learning/informal-essay/01.html

本文是由给私教学员 cava 讲解时编写,主要逻辑没有错误。

k-近邻算法(K-Nearest Neighbour algorithm),又称 KNN 算法,是数据挖掘技术中原理最简单的算法。

工作原理:给定一个已知标签类别的训练数据集,输入没有标签的新数据后,在训练数据集中找到与新数据最邻近的 k 个实例,如果这 k 个实例的多数属于某个类别,那么新数据就属于这个类别。简单理解为:由那些离 X 最近的 k 个点来投票决定 X 归为哪一类。

二、k-近邻算法的步骤

(1)计算已知类别数据集中的点与当前点之间的距离;

(2)按照距离递增次序排序;

(3)选取与当前点距离最小的 k 个点;

(4)确定前k个点所在类别的出现频率;

(5)返回前 k 个点出现频率最高的类别作为当前点的预测类别。

三、Python 实现

判断一个电影是爱情片还是动作片。

电影名称 搞笑镜头 拥抱镜头 打斗镜头 电影类型
0 功夫熊猫 39 0 31 喜剧片
1 叶问3 3 2 65 动作片
2 伦敦陷落 2 3 55 动作片
3 代理情人 9 38 2 爱情片
4 新步步惊心 8 34 17 爱情片
5 谍影重重 5 2 57 动作片
6 功夫熊猫 39 0 31 喜剧片
7 美人鱼 21 17 5 喜剧片
8 宝贝当家 45 2 9 喜剧片
9 唐人街探案 23 3 17

欧氏距离

构建数据集

rowdata = {
"电影名称": ['功夫熊猫', '叶问3', '伦敦陷落', '代理情人', '新步步惊心', '谍影重重', '功夫熊猫', '美人鱼', '宝贝当家'],
"搞笑镜头": [39,3,2,9,8,5,39,21,45],
"拥抱镜头": [0,2,3,38,34,2,0,17,2],
"打斗镜头": [31,65,55,2,17,57,31,5,9],
"电影类型": ["喜剧片", "动作片", "动作片", "爱情片", "爱情片", "动作片", "喜剧片", "喜剧片", "喜剧片"]
}

计算已知类别数据集中的点与当前点之间的距离

new_data = [24,67]
dist = list((((movie_data.iloc[:6,1:3]-new_data)**2).sum(1))**0.5)

将距离升序排列,然后选取距离最小的 k 个点「容易拟合·以后专栏再论」

k = 4
dist_l = pd.DataFrame({'dist': dist, 'labels': (movie_data.iloc[:6, 3])})
dr = dist_l.sort_values(by='dist')[:k]

确定前 k 个点的类别的出现概率

re = dr.loc[:,'labels'].value_counts()
re.index[0]

选择频率最高的类别作为当前点的预测类别

result = []
result.append(re.index[0])
result

四、约会网站配对效果判定

# 导入数据集
datingTest = pd.read_table('datingTestSet.txt',header=None)
datingTest.head() # 分析数据
%matplotlib inline
import matplotlib as mpl
import matplotlib.pyplot as plt #把不同标签用颜色区分
Colors = []
for i in range(datingTest.shape[0]):
m = datingTest.iloc[i,-1] # 标签
if m=='didntLike':
Colors.append('black')
if m=='smallDoses':
Colors.append('orange')
if m=='largeDoses':
Colors.append('red') #绘制两两特征之间的散点图
plt.rcParams['font.sans-serif']=['Simhei'] #图中字体设置为黑体
pl=plt.figure(figsize=(12,8)) # 建立一个画布 fig1=pl.add_subplot(221) # 建立两行两列画布,放在第一个里面
plt.scatter(datingTest.iloc[:,1],datingTest.iloc[:,2],marker='.',c=Colors)
plt.xlabel('玩游戏视频所占时间比')
plt.ylabel('每周消费冰淇淋公升数') fig2=pl.add_subplot(222)
plt.scatter(datingTest.iloc[:,0],datingTest.iloc[:,1],marker='.',c=Colors)
plt.xlabel('每年飞行常客里程')
plt.ylabel('玩游戏视频所占时间比') fig3=pl.add_subplot(223)
plt.scatter(datingTest.iloc[:,0],datingTest.iloc[:,2],marker='.',c=Colors)
plt.xlabel('每年飞行常客里程')
plt.ylabel('每周消费冰淇淋公升数')
plt.show() # 数据归一化
def minmax(dataSet):
minDf = dataSet.min()
maxDf = dataSet.max()
normSet = (dataSet - minDf )/(maxDf - minDf)
return normSet datingT = pd.concat([minmax(datingTest.iloc[:, :3]), datingTest.iloc[:,3]], axis=1)
datingT.head() # 切分训练集和测试集
def randSplit(dataSet,rate=0.9):
n = dataSet.shape[0]
m = int(n*rate)
train = dataSet.iloc[:m,:]
test = dataSet.iloc[m:,:]
test.index = range(test.shape[0])
return train,test train,test = randSplit(datingT) # 分类器针对约会网站的测试代码
def datingClass(train,test,k):
n = train.shape[1] - 1 # 将标签列减掉
m = test.shape[0] # 行数
result = []
for i in range(m):
dist = list((((train.iloc[:, :n] - test.iloc[i, :n]) ** 2).sum(1))**5)
dist_l = pd.DataFrame({'dist': dist, 'labels': (train.iloc[:, n])})
dr = dist_l.sort_values(by = 'dist')[: k]
re = dr.loc[:, 'labels'].value_counts()
result.append(re.index[0])
result = pd.Series(result)
test['predict'] = result # 增加一列
acc = (test.iloc[:,-1]==test.iloc[:,-2]).mean()
print(f'模型预测准确率为{acc}')
return test datingClass(train,test,5) # 95%

五、手写数字识别

import os

#得到标记好的训练集
def get_train():
path = 'digits/trainingDigits'
trainingFileList = os.listdir(path)
train = pd.DataFrame()
img = [] # 第一列原来的图像转换为图片里面0和1,一行
labels = [] # 第二列原来的标签
for i in range(len(trainingFileList)):
filename = trainingFileList[i]
txt = pd.read_csv(f'digits/trainingDigits/{filename}', header = None) #32行
num = ''
# 将32行转变为1行
for i in range(txt.shape[0]):
num += txt.iloc[i,:]
img.append(num[0])
filelable = filename.split('_')[0]
labels.append(filelable)
train['img'] = img
train['labels'] = labels
return train train = get_train() # 得到标记好的测试集
def get_test():
path = 'digits/testDigits'
testFileList = os.listdir(path)
test = pd.DataFrame()
img = [] # 第一列原来的图像转换为图片里面0和1,一行
labels = [] # 第二列原来的标签
for i in range(len(testFileList)):
filename = testFileList[i]
txt = pd.read_csv(f'digits/testDigits/{filename}', header = None) #32行
num = ''
# 将32行转变为1行
for i in range(txt.shape[0]):
num += txt.iloc[i,:]
img.append(num[0])
filelable = filename.split('_')[0]
labels.append(filelable)
test['img'] = img
test['labels'] = labels
return test test = get_test() # 分类器针对手写数字的测试代码
from Levenshtein import hamming def handwritingClass(train, test, k):
n = train.shape[0]
m = test.shape[0]
result = []
for i in range(m):
dist = []
for j in range(n):
d = str(hamming(train.iloc[j,0], test.iloc[i,0]))
dist.append(d)
dist_l = pd.DataFrame({'dist':dist, 'labels':(train.iloc[:,1])})
dr = dist_l.sort_values(by='dist')[:k]
re = dr.loc[:,'labels'].value_counts()
result.append(re.index[0])
result = pd.Series(result)
test['predict'] = result
acc = (test.iloc[:,-1] == test.iloc[:,-2]).mean()
print(f'模型预测准确率为{acc}')
return test handwritingClass(train, test, 3) # 97.8%

六、算法优缺点

优点

(1)简单好用,容易理解,精度高,理论成熟,既可以用来做分类也可以用来做回归;

(2)可用于数值型数据和离散型数据;

(3)无数据输入假定;

(4)适合对稀有事件进行分类。

缺点

(1)计算复杂性高;空间复杂性高;

(2)计算量大,所以一般数值很大的适合不用这个,但是单个样本又不能太少,否则容易发生误分;

(3)样本不平衡问题(即有些类别的样本数量很多,而其他样本的数量很少);

(4)可理解性比较差,无法给出数据的内在含义

欢迎关注我公众号:AI悦创,有更多更好玩的等你发现!

::: details 公众号:AI悦创【二维码】

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-WYM7nOC8-1662516904384)(/gzh.jpg)]

:::

::: info AI悦创·编程一对一

AI悦创·推出辅导班啦,包括「Python 语言辅导班、C++ 辅导班、java 辅导班、算法/数据结构辅导班、少儿编程、pygame 游戏开发」,全部都是一对一教学:一对一辅导 + 一对一答疑 + 布置作业 + 项目实践等。当然,还有线下线上摄影课程、Photoshop、Premiere 一对一教学、QQ、微信在线,随时响应!微信:Jiabcdefh

C++ 信息奥赛题解,长期更新!长期招收一对一中小学信息奥赛集训,莆田、厦门地区有机会线下上门,其他地区线上。微信:Jiabcdefh

方法一:QQ

方法二:微信:Jiabcdefh

:::

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-I9PiHP9R-1662516904384)(/zsxq.jpg)]

Python实现k-近邻算法案例学习的更多相关文章

  1. 机器学习 Python实践-K近邻算法

    机器学习K近邻算法的实现主要是参考<机器学习实战>这本书. 一.K近邻(KNN)算法 K最近邻(k-Nearest Neighbour,KNN)分类算法,理解的思路是:如果一个样本在特征空 ...

  2. 用python实现k近邻算法

    用python写程序真的好舒服. code: import numpy as np def read_data(filename): '''读取文本数据,格式:特征1 特征2 -- 类别''' f=o ...

  3. 用Python从零开始实现K近邻算法

    KNN算法的定义: KNN通过测量不同样本的特征值之间的距离进行分类.它的思路是:如果一个样本在特征空间中的k个最相似(即特征空间中最邻近)的样本中的大多数属于某一个类别,则该样本也属于这个类别.K通 ...

  4. 机器学习经典算法具体解释及Python实现--K近邻(KNN)算法

    (一)KNN依旧是一种监督学习算法 KNN(K Nearest Neighbors,K近邻 )算法是机器学习全部算法中理论最简单.最好理解的.KNN是一种基于实例的学习,通过计算新数据与训练数据特征值 ...

  5. 机器学习实战 - python3 学习笔记(一) - k近邻算法

    一. 使用k近邻算法改进约会网站的配对效果 k-近邻算法的一般流程: 收集数据:可以使用爬虫进行数据的收集,也可以使用第三方提供的免费或收费的数据.一般来讲,数据放在txt文本文件中,按照一定的格式进 ...

  6. python 机器学习(二)分类算法-k近邻算法

      一.什么是K近邻算法? 定义: 如果一个样本在特征空间中的k个最相似(即特征空间中最邻近)的样本中的大多数属于某一个类别,则该样本也属于这个类别. 来源: KNN算法最早是由Cover和Hart提 ...

  7. R语言学习笔记—K近邻算法

    K近邻算法(KNN)是指一个样本如果在特征空间中的K个最相邻的样本中的大多数属于某一个类别,则该样本也属于这个类别,并具有这个类别上样本的特性.即每个样本都可以用它最接近的k个邻居来代表.KNN算法适 ...

  8. 02机器学习实战之K近邻算法

    第2章 k-近邻算法 KNN 概述 k-近邻(kNN, k-NearestNeighbor)算法是一种基本分类与回归方法,我们这里只讨论分类问题中的 k-近邻算法. 一句话总结:近朱者赤近墨者黑! k ...

  9. 机器学习实战笔记(Python实现)-01-K近邻算法(KNN)

    --------------------------------------------------------------------------------------- 本系列文章为<机器 ...

  10. 机器学习——KNN算法(k近邻算法)

    一 KNN算法 1. KNN算法简介 KNN(K-Nearest Neighbor)工作原理:存在一个样本数据集合,也称为训练样本集,并且样本集中每个数据都存在标签,即我们知道样本集中每一数据与所属分 ...

随机推荐

  1. Containerd-1.6.5 镜像容器操作

    一.Containerd 镜像操作 1 基本参数 [root@ecs-65685 ~]# ctr c NAME: ctr containers - manage containers USAGE: c ...

  2. Mysql单表访问方法,索引合并,多表连接原理,基于规则的优化,子查询优化

    参考书籍<mysql是怎样运行的> 非常推荐这本书,通俗易懂,但是没有讲mysql主从等内容 书中还讲解了本文没有提到的子查询优化内容, 本文只总结了常见的子查询是如何优化的 系列文章目录 ...

  3. Linux实战笔记_CentOS7_yum相关配置

    配置yum源优先级 配置优先级 yum -y install yum-plugin-priorities.noarch vi /etc/yum.repos.d/localISO.repo priori ...

  4. 一天五道Java面试题----第八天(怎么处理慢查询--------->简述Myisam和innodb的区别)

    这里是参考B站上的大佬做的面试题笔记.大家也可以去看视频讲解!!! 文章目录 1.怎么处理慢查询 2.ACID靠什么保证的 3.什么是MVCC 4.mysql主从同步原理 5.简述Myisam和inn ...

  5. 齐博x1标签动态调用数据

    示例代码如下: {qb:tag name="news_list_page_listdata02" type="cms" union="fid" ...

  6. 5.websocket原理

      websocket协议原理 1.WebSocket协议是基于TCP的一种新的协议.WebSocket最初在HTML5规范中被引用为TCP连接,作为基于TCP的套接字API的占位符.它实现了浏览器与 ...

  7. ysoserial commonscollections3 分析

    cc3利用链如下: TrAXFilter(Templates templates) TemplatesImpl->newTransformer() TemplatesImpl->getTr ...

  8. v-debounce-throttle是一个vue防抖节流指令

    v-debounce-throttle是一个vue防抖节流指令 简介 v-debounce-throttle是一个vue防抖节流指令,控制单一事件的触发频率.其核心是拦截组件元素的v-on绑定事件,采 ...

  9. 八、docker compose容器编排

    一. Docker-Compose 1.1. 什么是Docker Compose Compose 项目是 Docker 官方的开源项目,负责实现 Docker 容器集群的快速编排,开源代码在 http ...

  10. CSS动画-transition/animation

    HTML系列: 人人都懂的HTML基础知识-HTML教程(1) HTML元素大全(1) HTML元素大全(2)-表单 CSS系列: CSS基础知识筑基 常用CSS样式属性 CSS选择器大全48式 CS ...