K-近邻算法(KNN) + Python实现

  1. K-近邻算法(KNN)概述

这是分类算法的其中一种,基本思想就是给定一组训练数据或者叫已有数据,每条数据由几个特征值+分类组成,比如很有名的iris数据集,很多地方都可以下载到。前面四个参数是花萼花瓣的长宽,最后一个是所属的花种,数据集里包含了150个采集的数据。
我们的问题就在于如果给出一组新的参数,比如[7.2, 3.6, 5.1, 2.5],那么需要判断他属于哪个种类
在这里插入图片描述
算法的基本思想也很简单,就是拿新的参数去跟150个已有参数组做比较,分别得出差别值,差别值越小越排前面。
然后就是K发挥作用了,我们要预设一个K的值(一般是不大于20的整数),意思就是取前K个相似的参数组,然后统计这些参数组里哪个种类占多数,也就意味着我们的新参数是符合哪个种类的。

比如按下图理解,红色三角代表种类setosa,蓝色方块是versicolor,我们新的参数组是绿色小圆圈。这些图形和绿色小圆圈的距离就代表了他们的相似程度,越近越相似。
如果我们选择K=3,那么中间实线圈里就是被选上的三个参数组,红色三角有两个,占多数,那么我们就预测这个绿色小圆圈应该是红色三角。
K=5的时候就扩展到了虚线部分,蓝色方块占了多数,我们的预测就变成了蓝色方块versicolor
在这里插入图片描述

那么现在还有一个没解决的问题,怎么计算相似程度?我们一般用欧式距离或者曼哈顿距离。
都是去算每个参数之间的差别,再和起来
在这里插入图片描述

  1. Python实现基于iris数据集的分类算法

再概括一下上面说的算法:
a. 分别计算测试数据与各个训练数据之间的距离(欧氏距离)
b. 把这些距离按升序排序
c. 选取距离最小的K个点
d. 统计这K个点里面各种类型出现的次数
e. 返回出现频率最高的种类作为预测分类

python代码如下,选择的测试数据是[7.2, 3.6, 5.1, 2.5], 选取的K是5

import pandas as pd
import numpy as np
import math
import operator

# Import data
data = pd.read_csv("iris.csv")
print(data.head())

# Calculate Euclidean distance
def euclideanDistance(data1, data2, length):
    distance = 0
    for x in range(length):
        distance += np.square(data1[x+1] - data2[x][0])
    return np.sqrt(distance);

# Apply KNN algorithm
def knn(trainingSet, testInstance, k):
    distances = {}
    sort = {}
    print(testInstance.shape)
    length = testInstance.shape[1]
    print(length)
    for x in range(len(trainingSet)):
        dist = euclideanDistance(trainingSet.iloc[x], testInstance, length)
        distances[x] = dist

    print(distances.items())
    sort = sorted(distances.items(), key=lambda item:item[1])

    neighbors = []

    for x in range(k):
        neighbors.append(sort[x][0])

    classVotes = {}

    for x in range(len(neighbors)):
        response = trainingSet.iloc[neighbors[x]][-1]

        if response in classVotes:
            classVotes[response] += 1
        else:
            classVotes[response] = 1

    sortedVotes = sorted(classVotes, key = operator.itemgetter(1), reverse=True)
    return (sortedVotes[0], neighbors)


# Testing Block
testSet = [[7.2, 3.6, 5.1, 2.5]]
test = pd.DataFrame(testSet)
print(test)
k = 5
result, neighbor = knn(data, test, k)
print(result)
print(neighbor)
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值