机器学习python之KNN

注:本文借鉴于《机器学习实战》这本书


对于KNN的介绍在这里就不详细说了,在我的另一篇文章有。简单来说,k-近邻算法采用测量不同特征值之间的距离方法进行分类。

1.K-近邻算法

优点:精度高、对异常值不敏感、无数据输入假定

缺点:计算复杂度高、空间复杂度高

适用数据范围:数值型和标称型


2.K-近邻算法一般流程

(1)收集数据:可以使用任何方法

(2)准备数据:距离计算所需要的数值,最好是结构化 的数据格式

(3)分析数据:可以使用任何方法

(4)训练数据:此步骤不适用于k-近邻算法

(5)测试数据:计算错误率

(6)使用算法:首先需要输入样本数据和结构化的输出结果,然后运行k-近邻算法判定输入数据分别属于哪个分类,最后应用对计算出的分类执行后续的处理


3.对未知类别属性的数据集中的每个点依次执行以下操作:

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

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

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

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

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


4.下面给出一些例子

(1)一个简单的预测

from numpy import *
import operator
import matplotlib
import matplotlib.pyplot as plt



def creatDataSet():
    group=array([ [1.0,1.1],[1.0,1.0],[0,0],[0,0.1] ])
    labels=['A','A','B','B']
    return group,labels

    
def classify(inX,dataSet,labels,k):
dataSetSize=dataSet.shape[0]
diffMat=tile(inX,(dataSetSize,1))-dataSet
sqDiffMat=diffMat**2
distance=sqDiffMat.sum(axis=1)**0.5
sortedDistIndicies=distance.argsort()
classCount={}
for i in range(k):
labelName=labels[sortedDistIndicies[i]]
classCount[labelName]=classCount.get(labelName,0)+1;
sortedClassCount=sorted(classCount.items(),key=operator.itemgetter(1),reverse=True)
return sortedClassCount[0][0]

group,labels=creatDataSet()
print group
print labels
print classify([0,0],group,labels,3)


结果:





(2)分类:

from numpy import *
import operator



def classify(inMat,dataSet,labels,k):
dataSetSize=dataSet.shape[0]
diffMat=tile(inMat,(dataSetSize,1))-dataSet
sqDiffMat=diffMat**2
distance=sqDiffMat.sum(axis=1)**0.5
sortedDistIndicies=distance.argsort()
classCount={}
for i in range(k):
labelName=labels[sortedDistIndicies[i]]
classCount[labelName]=classCount.get(labelName,0)+1;
sortedClassCount=sorted(classCount.items(),key=operator.itemgetter(1),reverse=True)
return sortedClassCount[0][0]


def file2Mat(filename):
    fr=open(filename)
    arrayOLines=fr.readlines()
    numberOfLines=len(arrayOLines)
    returnMat=zeros((numberOfLines,6))
    classLabelVector=[]
    index=0
    for line in arrayOLines:
        line = line.strip()
        listFromLine=line.split('   ')
        returnMat[index,:]=listFromLine[0:6]
        classLabelVector.append(int(listFromLine[-1]))
        index+=1
    return returnMat,classLabelVector;
def autoNorm(dataSet):
minVals=dataSet.min(0)
maxVals=dataSet.max(0)
ranges=maxVals-minVals
normMat=zeros(shape(dataSet))
size=normMat.shape[0]
normMat=dataSet-tile(minVals,(size,1))
normMat=normMat/tile(ranges,(size,1))
return normMat,minVals,ranges
def test(trainigSetFileName,testFileName):
trianingMat,classLabel=file2Mat(trainigSetFileName)
trianingMat,minVals,ranges=autoNorm(trianingMat)
testMat,testLabel=file2Mat(testFileName)
testSize=testMat.shape[0]
errorCount=0.0
for i in range(testSize):
result=classify((testMat[i]-minVals)/ranges,trianingMat,classLabel,3)
if(result!=testLabel[i]):
errorCount+=1.0
errorRate=errorCount/(float)(len(testLabel))
return errorRate;
if __name__=="__main__":
errorRate=test('TrainSet.txt','TestSet.txt')
print("the error rate is :%f"%(errorRate))  


结果:

结果不是很好,因为数据是我自己搞的。。。。

在这个编程过程中遇到了一些问题,在这里和大家分享以下,希望大家以后注意!

这是错误!

在将文本记录转换为Numpy的解析程序中,原书是listFromLine=line.split('\t'),为什么我这里没用这个呢?

这个是因为我的数据原因(我的数据的格式有问题不符合\t的要求)。所以以后用的时候要注意这个!

最后还说一个,python语言格式很主要!本人在编程时,格式搞错了怎么都找不到错,搞了半天!香菇!最后发现是多大了一个空格符!




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值