Python实现K-近邻算法的示例代码

目录
  • 一、介绍
  • 二、k-近邻算法的步骤
  • 三、Python 实现
  • 四、约会网站配对效果判定
  • 五、手写数字识别
  • 六、算法优缺点
    • 优点
    • 缺点

一、介绍

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)可理解性比较差,无法给出数据的内在含义

到此这篇关于Python实现K-近邻算法的示例代码的文章就介绍到这了,更多相关Python K近邻算法内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Python机器学习之KNN近邻算法

    一.KNN概述 简单来说,K-近邻算法采用测量不同特征值之间的距离方法进行分类 优点:精度高.对异常值不敏感.无数据输入假定 缺点:计算复杂度高.空间复杂度高 适用数据范围:数值型和标称2型 工作原理:存在一个样本数据集合,也称为训练样本集,并且样本集中每个数据都存在标签,即我们知道样本集中每一个数据与所属分类的对应关系(训练集).输入没有标签的新数据之后,将新数据的每个特征与样本集中数据对应的特征进行比较,然后算法提取样本集中特征最相似数据(最近邻)的分类标签(测试集).一般来说,我们只选择样

  • python实现KNN近邻算法

    示例:<电影类型分类> 获取数据来源 电影名称 打斗次数 接吻次数 电影类型 California Man 3 104 Romance He's Not Really into Dudes 8 95 Romance Beautiful Woman 1 81 Romance Kevin Longblade 111 15 Action Roob Slayer 3000 99 2 Action Amped II 88 10 Action Unknown 18 90 unknown 数据显示:肉眼判断

  • python机器学习基础K近邻算法详解KNN

    目录 一.k-近邻算法原理及API 1.k-近邻算法原理 2.k-近邻算法API 3.k-近邻算法特点 二.k-近邻算法案例分析案例信息概述 第一部分:处理数据 1.数据量缩小 2.处理时间 3.进一步处理时间 4.提取并构造时间特征 5.删除无用特征 6.签到数量少于3次的地点,删除 7.提取目标值y 8.数据分割 第二部分:特征工程 标准化 第三部分:进行算法流程 1.算法执行 2.预测结果 3.检验效果 一.k-近邻算法原理及API 1.k-近邻算法原理 如果一个样本在特征空间中的k个最相

  • Python实现KNN(K-近邻)算法的示例代码

    一.概述 KNN(K-最近邻)算法是相对比较简单的机器学习算法之一,它主要用于对事物进行分类.用比较官方的话来说就是:给定一个训练数据集,对新的输入实例,在训练数据集中找到与该实例最邻近的K个实例, 这K个实例的多数属于某个类,就把该输入实例分类到这个类中.为了更好地理解,通过一个简单的例子说明. 我们有一组自拟的关于电影中镜头的数据: 那么问题来了,如果有一部电影 X,它的打戏为 3,吻戏为 2.那么这部电影应该属于哪一类? 我们把所有数据通过图表显示出来(圆点代表的是自拟的数据,也称训练集:

  • Python机器学习实战之k-近邻算法的实现

    目录 K-近邻算法概述 工作原理 实施KNN算法 示例:手写识别系统 K-近邻算法概述 简单地说, k-近邻算法采用测量不同特征值之间的距离方法进行分类. k-近邻算法 优点:精度高.对异常值不敏感.无数据输入假定. 缺点: 计算复杂度高.空间复杂度高. 适用数据范围: 数值型和标称型. 工作原理 存在一个样本数据集合, 也称作训练样本集, 并且样本集中每个数据都存在标签, 知道样本集中每一数据与所属分类的对应关系. 输入没有标签的新数据后, 将新数据的每个特征与样本集中数据对应的特征进行比较,

  • 用python实现k近邻算法的示例代码

    K近邻算法(或简称kNN)是易于理解和实现的算法,而且是你解决问题的强大工具. 什么是kNN kNN算法的模型就是整个训练数据集.当需要对一个未知数据实例进行预测时,kNN算法会在训练数据集中搜寻k个最相似实例.对k个最相似实例的属性进行归纳,将其作为对未知实例的预测. 相似性度量依赖于数据类型.对于实数,可以使用欧式距离来计算.其他类型的数据,如分类数据或二进制数据,可以用汉明距离. 对于回归问题,会返回k个最相似实例属性的平均值.对于分类问题,会返回k个最相似实例属性出现最多的属性. kNN

  • Python实现K-近邻算法的示例代码

    目录 一.介绍 二.k-近邻算法的步骤 三.Python 实现 四.约会网站配对效果判定 五.手写数字识别 六.算法优缺点 优点 缺点 一.介绍 k-近邻算法(K-Nearest Neighbour algorithm),又称 KNN 算法,是数据挖掘技术中原理最简单的算法. 工作原理:给定一个已知标签类别的训练数据集,输入没有标签的新数据后,在训练数据集中找到与新数据最邻近的 k 个实例,如果这 k 个实例的多数属于某个类别,那么新数据就属于这个类别.简单理解为:由那些离 X 最近的 k 个点

  • python实现经典排序算法的示例代码

    以下排序算法最终结果都默认为升序排列,实现简单,没有考虑特殊情况,实现仅表达了算法的基本思想. 冒泡排序 内层循环中相邻的元素被依次比较,内层循环第一次结束后会将最大的元素移到序列最右边,第二次结束后会将次大的元素移到最大元素的左边,每次内层循环结束都会将一个元素排好序. def bubble_sort(arr): length = len(arr) for i in range(length): for j in range(length - i - 1): if arr[j] > arr[j

  • Python实现七大查找算法的示例代码

    查找算法 -- 简介 查找(Searching)就是根据给定的某个值,在查找表中确定一个其关键字等于给定值的数据元素.     查找表(Search Table):由同一类型的数据元素构成的集合     关键字(Key):数据元素中某个数据项的值,又称为键值     主键(Primary Key):可唯一的标识某个数据元素或记录的关键字 查找表按照操作方式可分为:         1.静态查找表(Static Search Table):只做查找操作的查找表.它的主要操作是:         ①

  • Python实现鸡群算法的示例代码

    目录 算法简介 Python实现鸡和鸡群 鸡群更新 优化迭代 测试 算法简介 鸡群算法,缩写为CSO(Chicken Swarm Optimization),尽管具备所谓仿生学的背景,但实质上是粒子群算法的一个变体. 简单来说,粒子群就是一群粒子,每个粒子都有自己的位置和速度,而且每个粒子都要受到最佳粒子的吸引,除了这两条规则之外,粒子之间完全平等,彼此之间除了位置和速度之外,完全相等. 当然,粒子群算法本身也是有仿生学背景的,据说灵感来自于鸟群觅食,这个当然不重要,无非是一群平等的粒子变成了一

  • python实现决策树ID3算法的示例代码

    在周志华的西瓜书和李航的统计机器学习中对决策树ID3算法都有很详细的解释,如何实现呢?核心点有如下几个步骤 step1:计算香农熵 from math import log import operator # 计算香农熵 def calculate_entropy(data): label_counts = {} for feature_data in data: laber = feature_data[-1] # 最后一行是laber if laber not in label_counts

  • Python实现12种降维算法的示例代码

    目录 为什么要进行数据降维 数据降维原理 主成分分析(PCA)降维算法 其它降维算法及代码地址 1.KPCA(kernel PCA) 2.LDA(Linear Discriminant Analysis) 3.MDS(multidimensional scaling) 4.ISOMAP 5.LLE(locally linear embedding) 6.t-SNE 7.LE(Laplacian Eigenmaps) 8.LPP(Locality Preserving Projections) 网

  • Python实现异常检测LOF算法的示例代码

    目录 背景 LOF算法 1.k邻近距离 2.k距离领域 3.可达距离 4.局部可达密度 5.局部异常因子 LOF算法流程 LOF优缺点 Python实现LOF PyOD Sklearn 大家好,我是东哥. 本篇和大家介绍一个经典的异常检测算法:局部离群因子(Local Outlier Factor),简称LOF算法. 背景 Local Outlier Factor(LOF)是基于密度的经典算法(Breuning et. al. 2000), 文章发表于 SIGMOD 2000, 到目前已经有 3

  • Python实现孤立随机森林算法的示例代码

    目录 1 简介 2 孤立随机森林算法 2.1 算法概述 2.2 原理介绍 2.3 算法步骤 3 参数讲解 4 Python代码实现 5 结果 1 简介 孤立森林(isolation Forest)是一种高效的异常检测算法,它和随机森林类似,但每次选择划分属性和划分点(值)时都是随机的,而不是根据信息增益或基尼指数来选择. 2 孤立随机森林算法 2.1 算法概述 Isolation,意为孤立/隔离,是名词,其动词为isolate,forest是森林,合起来就是“孤立森林”了,也有叫“独异森林”,好

随机推荐