KNN算法的Python实现

# KNN算法思路:

#-----------------------------------------------------#

#step1:读入数据,存储为链表

#step2:数据预处理,包括缺失值处理、归一化等

#step3:设置K值

#step4:计算待测样本与所有样本的距离(二值、序数、连续)

#step5:投票决定待测样本的类别

#step6:利用测试集测试正确率

#-----------------------------------------------------#

注:因为是python的初学者,可能很多高级的用法还不会,所以把python代码写的像C还请大家不要吐槽。同时希望大家指出其中的错误和有待提高的地方,大家一起进步才是最棒的。

说明:数据集采自著名UCI数据集库 http://archive.ics.uci.edu/ml/datasets/Adult

# Author :CWX
# Date :2015/9/1
# Function: A classifier which using KNN algorithm 

import math

attributes = {"age":0,"workclass":1,"fnlwg":2,"education":3,"education-num":4,
			 "marital-status":5,"occupation":6,"relationship":7,"race":8,
			 "sex":9,"capital-gain":10,"capital-loss":11,"hours-per-week":12,
			 "native-country":13,"salary":14
			}

def read_txt(filename):
#read data and convert it into list 
	items = []
	fp = open(filename,‘r‘)
	lines = fp.readlines()
	for line in lines:
		line = line.strip(‘\n‘)
		items.append(line)
	fp.close()

	i = 0
	b = []
	for i in range(len(items)):
		b.append(items[i].split(‘,‘))
	return b

def computeNa(items):
# detect missing value in list and handle it
# items - an whole list 
	for item in items[:]:
		if item.count(‘ ?‘) > 0:
			items.remove(item)
		# if item.count(‘ ?‘) >= -1:
		# 	items.remove(item)
	return items

def disCal(lst1,lst2,type):
# calculting distance between lst1 and lst2
	distance = 0;
	if type == "Manhattan" or type == "manhattan":
		for i in range(len(lst2) - 1):
			distance += abs(lst1[i] - lst2[i])
	elif type == "Elucildean" or type == "elucildean":
		for i in range(len(lst2) - 1):
			distance += math.sqrt((lst1[i] - lst2[i])**2)
	else:
		print "Error in type name"
		distance = -1
	return distance

def computeContinous(datalist,attribute):
# compute continous attributes in list
	min_val = int(datalist[0][attribute])
	max_val = int(datalist[0][attribute])
	for items in datalist:
		if int(items[attribute]) < min_val:
			min_val = int(items[attribute])
		elif int(items[attribute]) > max_val:
			max_val = int(items[attribute])
	for items in datalist[:]:
		items[attribute] = (int(items[attribute]) - min_val) / float(max_val - min_val)
	return datalist

def computeOrdinal(datalist,attribute,level):
# compute ordinal attribute in datalist
	level_dict = {}
	for i in range(len(level)):
		level_dict[level[i]] = float(i) / (len(level) - 1)
#		level_dict[level[i]] = i
	for items in datalist[:]:
		items[attribute] = level_dict[items[attribute]]
	return datalist

def KnnAlgorithm(dataTrain,sample,attribute,k):
	mergeData = dataTrain
	mergeData.append(sample)
	data = preProcessing(mergeData)
	distance = []
	for i in range(len(data)-2):
		distance.append(disCal(data[i],data[len(data)-1],"Elucildean"))
	copy_dis = distance[:] # notice : not copy_dis = distance ,if it will be wrong
	distance.sort()

	class_dict = {"Yes":0,"No":0}
	for i in range(k):
		index = copy_dis.index(distance[i])
		if data[index][attribute] == " >50K":
			class_dict["Yes"] += 1
		else:
			class_dict["No"] += 1
	if  class_dict["Yes"] > class_dict["No"]:
		print "sample‘s salary >50K"
	else:
		print "sample‘s salary <=50K"

def preProcessing(datalist):
	b = computeNa(datalist)

	b = computeContinous(b,attributes["age"])

	workclass_level = [" Private"," Self-emp-not-inc"," Self-emp-inc"," Federal-gov"," Local-gov"," State-gov"," Without-pay"," Never-worked"]
	b = computeOrdinal(b,attributes["workclass"],workclass_level)

	b = computeContinous(b,attributes["fnlwg"])

	education_level =[" Bachelors"," Some-college"," 11th"," HS-grad"," Prof-school",
				  " Assoc-acdm"," Assoc-voc"," 9th"," 7th-8th"," 12th"," Masters"," 1st-4th"," 10th"," Doctorate"," 5th-6th"," Preschool"] 
	b = computeOrdinal(b,attributes["education"],education_level)

	b = computeContinous(b,attributes["education-num"])

	marital_status_level = [" Married-civ-spouse"," Divorced"," Never-married"," Separated"," Widowed"," Married-spouse-absent"," Married-AF-spouse"] 
	b = computeOrdinal(b,attributes["marital-status"],marital_status_level) 

	occupation_level  = [" Tech-support"," Craft-repair"," Other-service"," Sales"," Exec-managerial"," Prof-specialty"," Handlers-cleaners",
					 " Machine-op-inspct"," Adm-clerical"," Farming-fishing"," Transport-moving"," Priv-house-serv"," Protective-serv"," Armed-Forces"]
	b = computeOrdinal(b,attributes["occupation"],occupation_level)

	relationship_level = [" Wife"," Own-child"," Husband"," Not-in-family"," Other-relative"," Unmarried"]
	b = computeOrdinal(b,attributes["relationship"],relationship_level)

	race_level = [" White"," Asian-Pac-Islander"," Amer-Indian-Eskimo"," Other"," Black"]
	b = computeOrdinal(b,attributes["race"],race_level)

	sex_level = [" Female", " Male"]
	b = computeOrdinal(b,attributes["sex"],sex_level)

	b = computeContinous(b,attributes["capital-gain"])

	b = computeContinous(b,attributes["capital-loss"])

	b = computeContinous(b,attributes["hours-per-week"])

	native_country_level = [" United-States"," Cambodia"," England"," Puerto-Rico"," Canada"," Germany"," Outlying-US(Guam-USVI-etc)"," India",
						" Japan"," Greece"," South"," China"," Cuba"," Iran"," Honduras"," Philippines"," Italy"," Poland"," Jamaica"," Vietnam"," Mexico"," Portugal",
						" Ireland"," France"," Dominican-Republic"," Laos"," Ecuador"," Taiwan"," Haiti"," Columbia"," Hungary"," Guatemala"," Nicaragua"," Scotland",
						" Thailand"," Yugoslavia"," El-Salvador"," Trinadad&Tobago"," Peru"," Hong"," Holand-Netherlands"]
	b = computeOrdinal(b,attributes["native-country"],native_country_level)
	return b

def assessment(dataTrain,dataTest,atrribute,k):
	mergeData = computeNa(dataTrain)
	len_train = len(mergeData)
	mergeData.extend(computeNa(dataTest))
	data = preProcessing(mergeData)
	len_test = len(data) - len_train
	res_dict = {"correct":0,"wrong":0}
	for i in range(len_test):
		distance = []
		class_dict = {"Yes":0,"No":0}
		for j in range(len_train):
			distance.append(disCal(data[j],data[i+len_train],"Elucildean"))
		copy_dis = distance[:]
		distance.sort()
		for m in range(k):
			index = copy_dis.index(distance[m])
			if data[index][atrribute] == " >50K":
				class_dict["Yes"] += 1
			else:
				class_dict["No"] += 1	  
		if class_dict["Yes"] > class_dict["No"] and mergeData[i+len_train][atrribute] == " >50K.": #Attention : in train data in the end of lines there is a "."
			res_dict["correct"]  += 1
		elif mergeData[i+len_train][atrribute] == " <=50K." and class_dict["Yes"] < class_dict["No"]:
			res_dict["correct"]  += 1
		else:
			res_dict["wrong"] += 1
	correct_ratio = float(res_dict["correct"]) / (res_dict["correct"] + res_dict["wrong"])
	print "correct_ratio = ",correct_ratio 

filename = "H:\BaiduYunDownload\AdultDatasets\Adult_data.txt"
#sample = [" 80"," Private"," 226802"," 11th"," 7"," Never-married"," Machine-op-inspct"," Own-child"," Black"," Male"," 0"," 0"," 40"," United-States"," <=50K"]
sample = [" 65"," Private"," 184454"," HS-grad"," 9"," Married-civ-spouse"," Machine-op-inspct"," Husband"," White"," Male"," 6418"," 0"," 40"," United-States"," >50K"]
# this samples salary <=50K#
# filename = "D:\MyDesktop-HnH\data.txt"
a = read_txt(filename)
print len(a)

k = 3
#KnnAlgorithm(a,sample,attributes["salary"],k)

trainName = "H:\BaiduYunDownload\AdultDatasets\Adult_test.txt" 
trainData = read_txt(trainName)
#preProcessing(trainData)
assessment(a,trainData,attributes["salary"],k)

结果:正确率 0.812416998672

运行时间 1小时20分钟

时间: 2024-12-09 20:10:34

KNN算法的Python实现的相关文章

分类算法——k最近邻算法(Python实现)(文末附工程源代码)

kNN算法原理 k最近邻(k-Nearest Neighbor)算法是比较简单的机器学习算法.它采用测量不同特征值之间的距离方法进行分类,思想很简单:如果一个样本在特征空间中的k个最近邻(最相似)的样本中大多数属于某一个类别,则该样本也属于这个类别. kNN算法的步骤 第一阶段:确定k值(指最近的邻居的个数),一般是一个奇数 第二阶段:确定距离度量公式.文本分类一般使用夹角余弦,得出待分类数据点和所有已知类别的样本点,从中选择距离最近的k个样本: 第三阶段:统计这k个样本点钟各个类别的数量 kN

KNN算法实现手写体区分

KNN算法在python里面可以使用pip install指令安装,我在实现之前查看过安装的KNN算法,十分全面,包括了对于手写体数据集的处理.我这里只是实现了基础的识别方法,能力有限,没有数据处理方法. 电脑太渣,没有自己训练数据集. 选取的数据集是已经处理好的. 如果自己要手动处理数据集,推荐mnist的.自己要写算法处理成图片. #! /usr/bin/env python # -*- coding:utf-8 -*- # Author: gjt import numpy as npfro

Python KNN算法

机器学习新手,接触的是<机器学习实战>这本书,感觉书中描述简单易懂,但对于python语言不熟悉的我,也有很大的空间.今天学习的是k-近邻算法. 1. 简述机器学习 在日常生活中,人们很难直接从原始数据本身获得所需信息.而机器学习就是把生活中无序的数据转换成有用的信息.例如,对于垃圾邮件的检测,侦测一个单词是否存在并没有多大的作用,然而当某几个特定单词同时出现时,再辅以考虑邮件的长度及其他因素,人们就可以更准确地判定该邮件是否为垃圾邮件. 机器学习分为监督学习和无监督学习,其中: (1)监督学

[Python] 应用kNN算法预测豆瓣电影用户的性别

应用kNN算法预测豆瓣电影用户的性别 摘要 本文认为不同性别的人偏好的电影类型会有所不同,因此进行了此实验.利用较为活跃的274位豆瓣用户最近观看的100部电影,对其类型进行统计,以得到的37种电影类型作为属性特征,以用户性别作为标签构建样本集.使用kNN算法构建豆瓣电影用户性别分类器,使用样本中的90%作为训练样本,10%作为测试样本,准确率可以达到81.48%. 实验数据 本次实验所用数据为豆瓣用户标记的看过的电影,选取了274位豆瓣用户最近看过的100部电影.对每个用户的电影类型进行统计.

机器学习经典算法详解及Python实现--K近邻(KNN)算法

(一)KNN依然是一种监督学习算法 KNN(K Nearest Neighbors,K近邻 )算法是机器学习所有算法中理论最简单,最好理解的.KNN是一种基于实例的学习,通过计算新数据与训练数据特征值之间的距离,然后选取K(K>=1)个距离最近的邻居进行分类判断(投票法)或者回归.如果K=1,那么新数据被简单分配给其近邻的类.KNN算法算是监督学习还是无监督学习呢?首先来看一下监督学习和无监督学习的定义.对于监督学习,数据都有明确的label(分类针对离散分布,回归针对连续分布),根据机器学习产

【机器学习算法实现】kNN算法__手写识别——基于Python和NumPy函数库

[机器学习算法实现]系列文章将记录个人阅读机器学习论文.书籍过程中所碰到的算法,每篇文章描述一个具体的算法.算法的编程实现.算法的具体应用实例.争取每个算法都用多种语言编程实现.所有代码共享至github:https://github.com/wepe/MachineLearning-Demo     欢迎交流指正! (1)kNN算法_手写识别实例--基于Python和NumPy函数库 1.kNN算法简介 kNN算法,即K最近邻(k-NearestNeighbor)分类算法,是最简单的机器学习算

KNN及其改进算法的python实现

一. 马氏距离 我们熟悉的欧氏距离虽然很有用,但也有明显的缺点.它将样品的不同属性(即各指标或各变量)之间的差别等同看待,这一点有时不能满足实际要求.例如,在教育研究中,经常遇到对人的分析和判别,个体的不同属性对于区分个体有着不同的重要性.因此,有时需要采用不同的距离函数. 如果用dij表示第i个样品和第j个样品之间的距离,那么对一切i,j和k,dij应该满足如下四个条件:    ①当且仅当i=j时,dij=0 ②dij>0 ③dij=dji(对称性) ④dij≤dik+dkj(三角不等式) 显

Python实现KNN算法

Python实现KNN算法 KNN算法的实际用处很多,主要用于分类阶段,是一个基础的分类算法.KNN主要基于距离的计算,一般可以在原始的欧氏空间中计算样本之间的距离.改进版本有:先特征提取到一个更加鉴别的空间中,然后计算距离:或者先使用metric learning度量学习的技术来获得一个鉴别的度量空间,然后计算样本间的马氏距离. 不管怎么说,KNN在很多算法的分类阶段都可以用到,我们这里用python实现KNN. 1. sklearn自带的KNN fromsklearn.neighborsim

Python 手写数字识别-knn算法应用

在上一篇博文中,我们对KNN算法思想及流程有了初步的了解,KNN是采用测量不同特征值之间的距离方法进行分类,也就是说对于每个样本数据,需要和训练集中的所有数据进行欧氏距离计算.这里简述KNN算法的特点: 优点:精度高,对异常值不敏感,无数据输入假定 缺点:计算复杂度高,空间复杂度高 适用数据范围:数值型和标称型(具有有穷多个不同值,值之间无序)    knn算法代码: #-*- coding: utf-8 -*- from numpy import * import operatorimport