KNN邻近算法与python实践

来源:互联网 发布:用友数据库重装 编辑:程序博客网 时间:2024/06/05 16:56

k邻近算法(k-NearestNeighbor)又成为KNN,属于分类算法中的一种。KNN通过计算新数据与历史样本数据中不同类别数据点间的距离,从而对新数据进行分类。换句话说,就是通过新数据与最邻近的k个数据点,来对新数据进行分析和分类。

环境:mac + python3.6.3(另外需要的第三方库请自行下载)
python KNN算法原理demo代码如下:

from numpy import *from PIL import Imageimport operatorfrom os import listdirimport timeimport os# 图片处理# pillow# 将bmp格式的图片转化为只有0和1的txt文本,这样就有了训练数据了def transformAllBmp2Txt():    rootdir = "手写体素材"    list = os.listdir(rootdir)  # 列出文件夹下所有的目录与文件    time1 = time.time()    for i in range(0, len(list)):        path = os.path.join(rootdir, list[i])        if os.path.isdir(path):            # 具体某个文件夹下的所有文件与目录            path_dir = os.listdir(path)            for index in range(0, len(path_dir)):                # 好吧,这里做一层保护                file = os.path.join(path, path_dir[index])                if os.path.isfile(file):                    bmp2txt(file)    time2 = time.time()    print("总共耗时:" + str(time2 - time1))def bmp2txt(file):    im = Image.open(file)    fileSplit = file.split("/")    # dir = "transdata/" + fileSplit[1] + "/"    dir = "transdata/"    if os.path.exists(dir) == False:        os.makedirs(dir)    destination_file = dir + fileSplit[2].split(".")[0] + ".txt"    fh = open(destination_file, "a")    width = im.size[0]    height = im.size[1]    # print("图片的模式为:" + im.mode)  # 此bmp模式为L,模式L”为灰色图像,它的每个像素用8个bit表示,0表示黑,255表示白    for i in range(0, width):        for j in range(0, height):            cl = im.getpixel((i, j))            if (cl == 0):                # 黑色,由于选择的bmp背景色是黑色,所以默认的是黑色                fh.write("0")            else:                fh.write("1")        fh.write("\n")    fh.close()    print(destination_file + "保存成功。。。")# 从列方向扩展# tile(a,(size,1))def knn(k, testdata, traindata, labels):    # testdata:一维数组[0,0,1,……]    # traindata:二维数组[[0,0,1……],[],]    # labels:一维列表,跟traindata一一对应    # 以下shape取的是训练数据的第一维,即其行数,也就是训练数据的个数    traindatasize = traindata.shape[0]    dif = tile(testdata, (traindatasize, 1)) - traindata    # tile()的意思是给一维的测试数据转为与训练数据一样的行和列的格式    sqdif = dif ** 2    # axis=1-----》横向相加的意思    sumsqdif = sqdif.sum(axis=1)    # sumsqdif在此时已经成为1维的了    distance = sumsqdif ** 0.5    sortdistance = distance.argsort()    # sortdistance为测试数据到各个训练数据的距离按近到远排序之后的结果    count = {}    for i in range(0, k):        vote = labels[sortdistance[i]]        # sortdistance[i]测试数据最近的K个训练数据的下标        # vote测试数据最近的K个训练数据的类别        count[vote] = count.get(vote, 0) + 1    sortcount = sorted(count.items(), key=operator.itemgetter(1), reverse=True)    return sortcount[0][0]# 加载数据def datatoarray(fname):    arr = []    fh = open(fname)    # 28表示图片像素中的宽和高,比如我这里的图片是28*28的像素,转成txt文本就是28行*28列    for i in range(0, 28):        thisline = fh.readline()        for j in range(0, 28):            arr.append(int(thisline[j]))    return arr# 建立一个函数取文件名前缀,为了验证用def seplabel(fname):    filestr = fname.split(".")[0]    label = int(filestr.split("_")[0])    return label# 建立训练数据def traindata():    labels = []    trainfile = listdir("traindata")    num = len(trainfile)    print("文件的总数为:" + str(num))    # 长度784(列),每一行存储一个文件    # 用一个数组存储所有训练数据,行:文件总数,列:784    # 28*28=784    trainarr = zeros((num, 784))    for i in range(0, num):        thisfname = trainfile[i]        thislabel = seplabel(thisfname)        labels.append(thislabel)        trainarr[i, :] = datatoarray("traindata/" + thisfname)    return trainarr, labels# 用测试数据调用KNN算法去测试,看是否能够准确识别def datatest():    n1 = 0    n2 = 0    time1 = time.time()    trainarr, labels = traindata()    testlist = listdir("testdata")    tnum = len(testlist)    # print(trainarr)    for i in range(0, tnum):        n1 += 1        thistestfile = testlist[i]        testarr = datatoarray("testdata/" + thistestfile)        thislabel = seplabel(thistestfile)        rknn = knn(3, testarr, trainarr, labels)        print(rknn)        if (thislabel == rknn):            n2 += 1    time2 = time.time()    print("耗时:" + str(time2 - time1) + "秒")    print("准确率:" + str(n2 / n1))# #抽某一个测试文件出来进行试验# trainarr,labels=traindata()# thistestfile="a.txt"# testarr=datatoarray("testdata/"+thistestfile)# #print(testarr)# rknn=knn(3,testarr,trainarr,labels)# print(rknn)datatest()# ------------------------------------------------------python算法原理结束-------------------------------------------------------

完整代码在python_study/w7-罗小辉-380226205/test_knn.py中,运行test_knn.py即可。

阅读全文
'); })();
0 0
原创粉丝点击
热门IT博客
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 女性痔疮症状 得痔疮有什么症状 痔疮有啥症状 早期痔疮 内痔疮图片早期 痔疮前兆 痔疮二期 痔疮是什么感觉 什么是内痔疮 混合痣 得了痔疮会怎么样 痔疮有什么表现 痣疮有哪些症状 痔疮的症状都有哪些 得痔疮 外痣 静脉曲张型外痔 环状痔 痣苍症状 肛裂和痔疮区别 哨兵痔 外痔症状 内外痔疮图片 屁眼痔疮 产妇痔疮 割痔疮后遗症 痔疮会肚子疼吗 屁股生痔疮怎么办 内外混合痔 嵌顿痔 痔疮大便 男性痔疮 吃什么可以缓解痔疮 轻微痔疮 痔疮一直流血 怎么得痔疮 便秘痔疮 女生痔疮怎么办 痔疮不管它会怎么样 痔疮破裂 便血痔疮