• 2机器学习实践笔记(k-最近邻)


    1:算法是简单的叙述说明

           由于训练数据样本和标签,为测试数据的示例,从最近的距离k训练样本,此k练样本中所属类别最多的类即为该測试样本的预測标签。

    简称kNN。通常k是不大于20的整数,这里的距离通常是欧式距离。

    2:python代码实现

    创建一个kNN.py文件,将核心代码放在里面了。

    (1)   创建数据

    #创造数据集
    def createDataSet():
        group = array([[1.0, 1.1], [1.0, 1.0], [0, 0], [0, 0.1]])
        labels = ['A', 'A', 'B', 'B']
        return group, labels

    (2)   构照kNN分类器

    #第一个kNN分类器  inX-測试数据 dataSet-样本数据  labels-标签 k-邻近的k个样本
    def classify0(inX,dataSet, labels, k):
        #计算距离
        dataSetSize = dataSet.shape[0]
        diffMat = tile(inX, (dataSetSize,1))- dataSet
        sqDiffMat = diffMat ** 2
        sqDistances = sqDiffMat.sum(axis = 1)
        distances = sqDistances **0.5
        sortedDistIndicies = distances.argsort()
        classCount = {}
        #选择距离最小的k个点
        for i in range(k):
            voteIlabel = labels[sortedDistIndicies[i]]
            classCount[voteIlabel] = classCount.get(voteIlabel,0)+1
        #排序
        sortedClassCount = sorted(classCount.iteritems(), key = operator.itemgetter(1),reverse = True)
        return sortedClassCount[0][0]

    代码解说:(a)tile函数 tile(inX, i);扩展长度  tile(inX, (i,j)) ;i是扩展个数,j是扩展长度。

    如:

                          

                    (b) python代码路径。须要导入os文件,os.getcwd()显示当前文件夹。os.chdir(‘’)改变文件夹,listdir()显示当前文件夹的全部文件。

    此外假设改动了当前.py文件,须要在python shell中又一次载入该py文件(reload(kNN.py)),以确保更新的内容能够生效。否则python将继续使用上次载入的kNN模块。如:

     


              (c)注意列表求平方,求和

               如:

    3:案例—约会站点

    案例描写叙述:

    (1)   从文本文件里解析数据

    # 将文本记录到转换numPy的解析程序
    def file2matrix(filename):
        #打开文件并得到文件行数
        fr = open(filename)
        arrayOLines = fr.readlines()
        numberOfLines = len(arrayOLines)
        #创建返回的numPy矩阵
        returnMat = zeros((numberOfLines, 3))
        classLabelVector = []
        index =0
        #解析文件数据到列表
        for line in arrayOLines:
            line = line.strip()
            listFormLine = line.split('	')
            returnMat[index,:] = listFormLine[0:3]
            classLabelVector.append(int(listFormLine[-1]))
            index += 1
        return returnMat, classLabelVector

    代码解说:(a)首先使用函数line.strip()截取掉全部的回车字符,然后使用tab字符 将上一步得到的整行数据切割成一个元素列表

              (b)int(listFormLine[-1]);python中能够使用索引值-1表示列表中的最后一列元素。此外这里我们必须明白的通知解释器,告诉它列表中存储的元素值为整型。否则python语言会将这些元素当做字符串处理。

    (2)使用画图工具matplotlib创建散点图—能够分析数据




    (3)归一化数值

       为了防止特征值数量的差异对预測结果的影响(比方计算距离,量值较大的特征值影响肯定非常大)。我们将全部的特征值都归一化到[0,1]

    #归一化特征值
    def autoNorm(dataSet):
        minVals = dataSet.min(0);
        maxVals = dataSet.max(0);
        ranges = maxVals - minVals;
        normDataSet = zeros(shape(dataSet))
        m = dataSet.shape[0]
        normDataSet = dataSet - tile(minVals, (m,1))
        normDataSet = normDataSet/tile(ranges,(m,1))
        return normDataSet, ranges, minVals
    

    (4)測试代码

         測试代码以90%的作为训练样本。10%的作为測试数据

    #測试代码
    def datingClassTest():
        hoRatio = 0.10    #測试数据占的百分比
        datingDataMat, datingLabels = file2matrix('datingTestSet2.txt')
        normMat, ranges, minVals = autoNorm(datingDataMat)
        m = normMat.shape[0]
        numTestVecs = int(m*hoRatio)
        errorCount = 0.0
        for i in range(numTestVecs):
            classifierResult = classify0(normMat[i,:], normMat[numTestVecs:m,:],datingLabels[numTestVecs:m],3)
            print 'the classifier came back with: %d, the real answer is: %d' %(classifierResult, datingLabels[i])
            if(classifierResult != datingLabels[i]): errorCount += 1.0
        print "the total error rate is: %f " % (errorCount/float(numTestVecs))

    (5)输入某人的信息。便得出对对方的喜欢程度

    #输入某人的信息,便得出对对方喜欢程度的预測值
    def classifyPerson():
        resultList = ['not at all', 'in small doses', 'in large doses']
        percentTats = float(raw_input("percentage of time spent playing video games?

    ")) ffMiles = float(raw_input("frequent flier miles earned per year?

    ")) iceCream = float(raw_input("liters of ice cream consumed per year?

    ")) datingDataMat, datingLabels = file2matrix('datingTestSet2.txt') normMat, ranges, minVals = autoNorm(datingDataMat) inArr = array([ffMiles, percentTats, iceCream]) classifierResult = classify0((inArr - minVals)/ranges, normMat, datingLabels,3) print 'You will probably like this person: ', resultList[classifierResult - 1]

    代码解说:python中raw_input同意用户输入文本行命令并返回用户所输入的命令

     

    4:案例—手写识别系统

            这里能够将手写字符看做由01组成的32*32个二进制文件,然后转换为1*1024的向量即为一个训练样本。每一维即为一个特征值

    (1)   将一个32*32的二进制图像转换成1*1024的向量

    #将一个32*32的二进制图像矩阵转换成1*1024的向量
    
    def img2vector(filename):
        returnVect = zeros((1,1024))
        fr = open(filename)
        for i in range(32):
            lineStr = fr.readline()
            for j in range(32):
                returnVect[0, 32*i+j] = int(lineStr[j])
        return returnVect

    (2)   手写识别系统測试代码

    #手写识别系统測试代码
    def handwritingClassTest():
        hwLabels = []
        trainingFileList = listdir('trainingDigits')   #获取文件夹内容
        m = len(trainingFileList)
        trainingMat = zeros((m, 1024))
        for i in range(m):
            fileNameStr = trainingFileList[i]              #切割得到标签  从文件名称解析得到分类数据
            fileStr = fileNameStr.split('.')[0]
            classStr = int(fileStr.split('_')[0])
            hwLabels.append(classStr)                 #測试例子标签
            trainingMat[i,:] = img2vector('trainingDigits/%s' % fileNameStr)
        testFileList = listdir('testDigits')
        errorCount = 0.0
        mTest = len(testFileList)
        for i in range(mTest):
            fileNameStr = testFileList[i]
            fileStr = fileNameStr.split('.')[0]
            classStr = int(fileStr.split('_')[0])
            vectorUnderTest = img2vector('testDigits/%s' % fileNameStr)
            classifierResult = classify0(vectorUnderTest, trainingMat, hwLabels, 3)
            print 'the classifier came back with: %d, the real answer is: %d' % (classifierResult, classStr)
            if(classifierResult != classStr): errorCount += 1.0
        print "
    the total numbers of errors is : %d" % errorCount
        print "
    the total error rate is: %f" % (errorCount/float(mTest))
            

    注明:1:本笔记来源于书籍<机器学习实战>

    2:kNN.py文件及笔记所用数据在这下载(http://download.csdn.net/detail/lu597203933/7653991).

    作者:小村长  出处:http://blog.csdn.net/lu597203933 欢迎转载或分享。但请务必声明文章出处。

    (新浪微博:小村长zack, 欢迎交流!

    版权声明:本文博客原创文章,博客,未经同意,不得转载。

  • 相关阅读:
    Python字符编码详解
    Python 编程规范
    希尔排序
    浅析 Python 的 metaclass
    c#通过数据集生成浏览页面
    QQ搜索群参数详解
    扩展名为HTM或HTML的文件图标不能正常显示的解决方案
    利用QQ2009协议,将抓包直接解密出ClientKey(SessionKey)
    用Sql语句还原,分离,删除数据库连接
    asp.net 导出excel 问题 (服务器的部署)
  • 原文地址:https://www.cnblogs.com/bhlsheji/p/4748870.html
Copyright © 2020-2023  润新知