机器学习-分类算法-kNN

机器学习-分类算法-kNN

kNN(k-Nearest Neighbor)算法:一种基于向量间相似度的分类算法。

kNN原理

k最近邻(k-Nearest Neighbor)算法是比较简单的机器学习算法。它采用测量不同特征之间的距离方法进行分类。

如果一个样本在特征空间中的k个最近邻(最相似)的样本中的大多数都属于一个类别,则该样本也属于这个类别。k表示外部定义的近邻数量。

实现步骤

第一阶段:确定k值(就是指最近邻居的个数)。一般是奇数个

第二阶段:确定距离度量公式。文本分类一般使用夹角余弦,得出待分类数据点和所有已知类别的样本点,从中选择距离最近的k个样本。

夹角余弦:cos = AB/|A||B|

第三阶段:统计这k个样本点中各个类别的数量。根据k个样本中数量最多的样本是什么类别,我们就把这个数据点定为什么类别。

实现代码1(训练集为一组事件发生概率,测试集为事件发生概率,求类型)

from numpy import *
import operator

# 夹角余弦距离公式
def consdist(vector1, vector2):
    print("vecotr1:",vector1)
    print("vector2:",vector2)
    result = dot(vector1, vector2) / (linalg.norm(vector1) * linalg.norm(vector2))
    print("result:", result)
    return result


# KNN分类器
# testData:测试集  trainSet:训练集    listClasses:类别标签    k:k个邻居
def classify(testData, trainSet, listClasses, k):
    dataSetSize = trainSet.shape[0] # 返回样本的行数
    distances = array(zeros(dataSetSize))
    print("dataSetSize:", dataSetSize)
    for indx in range(dataSetSize): # 计算测试集和训练集之间的距离:余弦夹角
        distances[indx] = consdist(testData, trainSet[indx])
    # 根据生成的余弦夹角按从大到小排序,结果为索引号
    sortedDistIndics = argsort(-distances)
    classCount = {}
    for i in range(k):  # 获得角度最小的前K项作为参考项
        # 按排序顺序返回样本集对应的类别标签
        voteIlabel = listClasses[sortedDistIndics[i]]
        # 为字典classCount赋值,相同key,其中value加1
        classCount[voteIlabel] = classCount.get(voteIlabel, 0) + 1  # 获得voteIlabel的value值,没有则默认为0
    # 对分类字典classCount按value重新排序
    # sorted(data.items(), key = operator.itemgetter(1), reverse = True)
    # 该句是按字典排序的固定用法
    # classCount.items()  # 字典迭代器函数
    # key:排序参数  operator.itemgetter(1):多级排序
    sortedClassCount = sorted(classCount.items(), key=operator.itemgetter(1), reverse=True)
    return sortedClassCount[0][0]   # 返回序最高的一项

dataArr = np.array([[0.238, 0, 0.1905, 0.1905, 0.1905, 0.1905], [0, 0.177, 0, 0.294, 0.235, 0.294], [0.2, 0.16, 0.12, 0.12, 0.2, 0.2]])
dataMat = mat(dataArr)
print("dataMat:", dataMat.shape)
print("dataMat type:", type(dataMat))
testSet = [0.2174, 0.2174, 0.1304, 0, 0.2174, 0.2174]
testMat = mat(testSet)
classLabel = [0, 1, 2]
k = 3
print("result:",classify(testSet, dataArr, classLabel, k))

实现代码2(文本测试)

# K近邻分类
from numpy import  *
import numpy as np
import operator

from com.machineLearning.Bayes.NBayes import NBayes


def loadDataSet():
    # 训练集文本
    postingList = [
        ['my', 'dog', 'has', 'flea', 'problems', 'help', 'please'],
        ['maybe', 'not', 'take', 'him', 'to', 'dog', 'park', 'stupid'],
        ['my', 'dalmation', 'is', 'so', 'cute', 'I', 'love', 'him', 'my'],
        ['stop', 'posting', 'stupid', 'worthless', 'garbage'],
        ['mr', 'licks', 'ate', 'my', 'steak', 'how', 'to', 'stop', 'him'],
        ['quit', 'buying', 'worthless', 'dog', 'food', 'stopid']
    ]
    # 每个文本对应的分类
    classVec = [0, 1, 0, 1, 0, 1]
    return postingList, classVec


# 夹角余弦距离公式
def consdist(vector1, vector2):
    return dot(vector1, vector2) / (linalg.norm(vector1) * linalg.norm(vector2))


# KNN分类器
# testData:测试集  trainSet:训练集    listClasses:类别标签    k:k个邻居
def classify(testData, trainSet, listClasses, k):
    dataSetSize = trainSet.shape[0] # 返回样本的行数
    distances = array(zeros(dataSetSize))
    for indx in range(dataSetSize): # 计算测试集和训练集之间的距离:余弦夹角
        distances[indx] = consdist(testData, trainSet[indx])
    # 根据生成的余弦夹角按从大到小排序,结果为索引号
    sortedDistIndics = argsort(-distances)
    classCount = {}
    for i in range(k):  # 获得角度最小的前K项作为参考项
        # 按排序顺序返回样本集对应的类别标签
        voteIlabel = listClasses[sortedDistIndics[i]]
        # 为字典classCount赋值,相同key,其中value加1
        classCount[voteIlabel] = classCount.get(voteIlabel, 0) + 1  # 获得voteIlabel的value值,没有则默认为0
    # 对分类字典classCount按value重新排序
    # sorted(data.items(), key = operator.itemgetter(1), reverse = True)
    # 该句是按字典排序的固定用法
    # classCount.items()  # 字典迭代器函数
    # key:排序参数  operator.itemgetter(1):多级排序
    sortedClassCount = sorted(classCount.items(), key = operator.itemgetter(1), reverse=True)
    return sortedClassCount[0][0]   # 返回序最高的一项


# 使用KNN算法实现文本分类
k = 3
dataSet, lisClasses = loadDataSet()
nb = NBayes()
nb.train_set(dataSet, lisClasses)
# 使用之前的贝叶斯分类阶段的数据集及生成的TF向量进行分类
print(classify(nb.tf[3], nb.tf, lisClasses, k))
NBayes看上一篇。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值